regular expressions at its best

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
Antworten
anogayales
User
Beiträge: 456
Registriert: Mittwoch 15. April 2009, 14:11

Hi Community,

ich bin drauf und dran eine Datei zu parsen. Dabei will ich reguläre Ausdrücke benutzen, weil sie hier einfach funktionieren.

Ich habe bereits ein bisschen daran gearbeitet, finde aber keine wirklich elgeante Lösung.

Das ganze ist eine java script Datei - glaube ich zumindest und hat folgendes Schema.

Code: Alles auswählen

hallo[12345] = ["Blablabla"]
hallo[316919] = ["Noch mehr text"]
hallo[123412125] = ["Noch viel mehr text als zuvor"]
Mein erster Ansatz war, dass ganze direkt als python code zu interpretieren. Ein dict namens hallo anlegen und alles in eine eval() methode packen. Das ist natürlich äußerst unsicher, also habe ich die Idee sofort verworfen.

Dann habe ich mich an reguläre Ausdrücke rangewagt und mit auf folgendes gekommen:
Sei im folgenden a eine Zeile des Strings



Code: Alles auswählen

re.findall(r"\[[0-9]*\]", a) #['[12345]']
Wie kriege ich hier zusätzlich die "[", "]" weg?

Frage ist jetzt, wie komme ich an den zweiten Teil?

Wie ihr sieht bin ich ein ziehmlicher Neuling, wenn es zu re kommt.

Es wäre nett, wenn ihr mir ein bisschen Helfen könntet.

Wie kann ich zum Beispiel sagen, finde alles was rechts von "= [" danach können beliebige Zeichen kommen, sobald "]" höre auf? Ich weiß, ich denk hier mehr wie ein endlicher automat :)

Grüße,
anogayales
Benutzeravatar
/me
User
Beiträge: 3555
Registriert: Donnerstag 25. Juni 2009, 14:40
Wohnort: Bonn

anogayales hat geschrieben:Wie kann ich zum Beispiel sagen, finde alles was rechts von "= [" danach können beliebige Zeichen kommen, sobald "]" höre auf?
Ganz, ganz einfach. ;-)

1. suche ein Gleichheitszeichen
2. suche beliebig viele Leerzeichen
3. suche ein [
4. suche und merke dir beliebig viele Zeichen die nicht ] sind

Code: Alles auswählen

foo = ' [9764327]  =  ["oasdsas"] # ["agfdgdffff"]'
m = re.search(r"=\s*\[([^\]]*)", foo)
print(m.group(1))
anogayales
User
Beiträge: 456
Registriert: Mittwoch 15. April 2009, 14:11

Ah cool,

sauber,

wenn ich dann nach dem ersten Teil (9764327) suchen will, muss ich einfach

Code: Alles auswählen

m = re.search(r"\[([^\]]*)", foo)
machen!

Wie siehts mit \n aus zwischen den einzelnen Einträgen, muss ich vorher die Datei in Zeilen aufteilen und dann jeweils auf jede Zeile anwenden.

Wie würdet ihr das geschickt machen?

Einfach den Text durchgehen und wenn ein \n kommt den bisherigen Text ein eine Zeile stopfen, die man als Liste verwaltet?

So?

Code: Alles auswählen

lines = []
temp = ""

for letter in input:
    
    
    if letter != "\n":
        temp = temp + letter
    else:
        lines.append(temp)
        temp = ""
        
print lines
geht es noch pythoniker?
vespe
User
Beiträge: 5
Registriert: Mittwoch 2. Dezember 2009, 12:20

Wenn du mit deinem regex weitermachen willst, musst du dir mal hier schauen.
Benutzeravatar
/me
User
Beiträge: 3555
Registriert: Donnerstag 25. Juni 2009, 14:40
Wohnort: Bonn

anogayales hat geschrieben: Wie siehts mit \n aus zwischen den einzelnen Einträgen, muss ich vorher die Datei in Zeilen aufteilen und dann jeweils auf jede Zeile anwenden.
Du kannst jede Zeile einzeln durchgehen (und das ist dein Codeansatz in einer pythonesken Form):

Code: Alles auswählen

with open("filename", "r") as fp:
    for line in fp:
        # tu was
Du kannst auch die komplette Datei am Stück einlesen und eine regular expression mit findall() und dem MULTILINE-Flag verwenden. Den Link zur Doku hat vespe schon gepostet.
Panke
User
Beiträge: 185
Registriert: Sonntag 18. März 2007, 19:26

anogayales
User
Beiträge: 456
Registriert: Mittwoch 15. April 2009, 14:11

Wie kann ich den nach " suchen?

r"\"" ging leider nicht
EyDu
User
Beiträge: 4881
Registriert: Donnerstag 20. Juli 2006, 23:06
Wohnort: Berlin

Doch, das geht. Du solltest villeicht den ganzen Ausdruck zeigen, den String gegen den gematcht wird, das Ergebnis und was du erwartest.
Das Leben ist wie ein Tennisball.
anogayales
User
Beiträge: 456
Registriert: Mittwoch 15. April 2009, 14:11

So,

ich hab mal wieder Zeit gefunden, und habe ein wenig herum experimentiert :)

Der String um den es geht sieht so aus:

"Hallo - Test"

(mit Anführungszeichen)

Bin das ganze jetzt so angegangen:
-\s*[^"]*

jetzt bekomm ich aber das "- " mit geliefert. Im obigen Beispiel wird das aber komischerweise nicht mit in die Gruppe genommen. Ich möchte lediglich den String "Test" bekommen.

Es wäre nett, wenn mir jemand helfen könnte :)

Grüße,
anogayales
Benutzeravatar
HWK
User
Beiträge: 1295
Registriert: Mittwoch 7. Juni 2006, 20:44

Dann mach doch mal runde Klammern um den Ausdruck, den Du als Ergebnis haben möchtest.
MfG
HWK
anogayales
User
Beiträge: 456
Registriert: Mittwoch 15. April 2009, 14:11

Bingo!

Danke!

Ich hab aber immer noch nicht verstanden, wie ich eine beliebige Zeichenfolge zulasse. ein []* tut leider nicht. [\w] und solche Geschichten schränken ja die Definition von "beliebige Zeichenfolge" ein.

Irgendwelche Vorschläge? :)
Benutzeravatar
HerrHagen
User
Beiträge: 430
Registriert: Freitag 6. Juni 2008, 19:07

Beliebige Zeichen matchen mit: Demnach steht für eine beliebige Anzahl von beliebigen Zeichen. Wirklich beliebig allerdings nur wenn das DOTALL-flag gesetzt wurde. Ansonsten fallen Zeilenumbrüche nicht da drunter.
anogayales
User
Beiträge: 456
Registriert: Mittwoch 15. April 2009, 14:11

Wie benutze ich das?

mit:

Code: Alles auswählen

string = "Hallo - ich bins - noch was"
compile_obj = re.compile(r"Hallo - ([-]*)")
match_obj = compile_obj.search(string)

print match_obj.group(1)
bekomme ich kein Ergenis. bzw. man muss ja das minus Zeichen von dem Kontrollzeichen unterscheiden können? Mit einem \ davor geht es auch nicht!

Danke!
Benutzeravatar
/me
User
Beiträge: 3555
Registriert: Donnerstag 25. Juni 2009, 14:40
Wohnort: Bonn

anogayales hat geschrieben:Wie benutze ich das?
Dir wurde .* als Ausdruck genannt und du verwendest den völlig anderen Ausdruck [-]* und fragst dann warum es nicht funktioniert? Was meinst du überhaupt mit Kontrollzeichen?

Ich verstehe aber durchaus, dass reguläre Ausdrücke nicht ganz einfach sind. Vielleicht solltest du mal in die Dokumentation schauen.
anogayales
User
Beiträge: 456
Registriert: Mittwoch 15. April 2009, 14:11

Ah, ich habe . mit - vertauscht :)

Ich dachte man muss wenn man \s \W usw. benutzt immer das ganze in [] schreiben

Was wäre denn wenn ich nur nach einem . und einem Stern suchen wollte?
Das habe ich mit Kontrollzeichen gemeint, man muss ja einmal von richtigen Zeichen und "Kontrollzeichen" unterscheiden!
Leonidas
Python-Forum Veteran
Beiträge: 16025
Registriert: Freitag 20. Juni 2003, 16:30
Kontaktdaten:

anogayales hat geschrieben:Ich dachte man muss wenn man \s \W usw. benutzt immer das ganze in [] schreiben
Nein. Du solltest echt mal ein Tutorial zu Regex lesen statt alles durch Zufall zu entdecken...
My god, it's full of CARs! | Leonidasvoice vs (former) Modvoice
Benutzeravatar
/me
User
Beiträge: 3555
Registriert: Donnerstag 25. Juni 2009, 14:40
Wohnort: Bonn

anogayales hat geschrieben:Was wäre denn wenn ich nur nach einem . und einem Stern suchen wollte?
Dann musst der der Regexp-Engine mitteilen, dass der Punkt als Punkt und der Stern als Stern interpretiert werden soll.Das wiederum machst du mit dem passenden Escape-Zeichen das du in der Dokumentation inzwischen sicher längst gefunden hast.
Antworten