Regex Order unwichtig bei Lookaheads?

berndoa

Top Contributor
Hallo,
ich verzweifle gerade am Bauen von Regex Ausdrücken.
Ich habe 2-3 bedingungen, die ich erfüllt haben will.
Also bspw. habe ich sowas wie

Python:
    r"(?i)(?=.*"
    r"(?: be | breakeven | break even )"
    r".*)(?=.*"
    r"(?: move )+"
    r".*)(?=.*"
    r" (?P<sl>stoploss|sl) "
    r".*)(?=.*"
    r" (?P<pair>[a-zA-Z]+[\/\.\\]*[a-zA-Z]+)? "
    r".*)"

Also 3 regex ausdrücke die, hoffentlich die 3 Bedingungen
enhält be, breakeven oder break even
enthält mindestens einmal move
enthält ein pair (die syntax dort stimmt garantiert, buchstaben, dann optional ein sonderzeichen, dann wieder buchstaben. und das optional weil nicht zwingend ein pair vorkommen muss)


nur scheitere ich am banalsten:
Wie kriege ich es hin dass jeder string gematcht wird der die 3 bedingungen in irgendeiner reihenfolge erfüllt?
Ohne jetzt ernsthaft jede mögliche reihenfolge von bedingungen explizit aufzuschreiben und zu verodern?

Ich kapiere auch nicht wirklich wie das mit diesen lookaheads, lookbehind etc. funktioneirt und wie ich die da für meine zwecke nutzen kann.
Named und unnamed capture groups checke ich noch und kriege ich recht zuverlässig hin, aber darüber hinaus verzweifle ich.

kann mir da jemand so das generelle muster sagen, wie man das hinkriegt, mehrere unter-regex miteinander zu kombinieren dass die in jeder reihenfolge erkannt werden?
 
Das wird mir zu kompliziert - ich würde es anders lösen:
3 eigene Regex-Ausdrücke für deine Bedingungen und dann im if Statement einfach alle drei abfragen. Man muss das nicht zwangsweise in in einen komprimieren.
 
hm, aber es soll ja dem muster folgen...
habe da so einen string wie: (newline charcters sind an den entsprechenden Zeilenumbrüchen)
Code:
Sell BTC.USD 41300

TP 1 41200

TP 2 41100

SL 41600

wenn wir jetzt nur mal die 1. zeile angucken.

die 3 ausdrücke direction (eben ob sell oder buy) das pair (Btc.Usd, usdaux, etc.) und die zahl dahinter könnte ja in 3!=6 verschiedenen kombinationen auftreten.

dann müsste ich 6 regexabfragen für jeden ausduck machen und mit if der reihe nach abfragen.

wenn noch die restlichen zeilen auch einige mögliche varianten aufweisen wie deren bestandteile hintereinaner stehen könnten, dann gute Nacht.


Chatgpt behauptet zumindest, mit dem eingänglichen Ausdruck würde ich sowohl sowas wie Sell BTC.USD 41300
als auch BTC.USD Sell 41300 abfangen. aberobs stimmt, keine ahnung. weil ich nciht ganz durchblicke wie diese lookaheads und lookbehinds überhaupt funktionieren.
 
Chatgpt behauptet zumindest
Alles was dahinter kommt kann man üblicherweise ignorieren, grad wenn es darum geht, ob irgendwas richtig ist, sind LLMs absolut ungeeignet.


Um mal zum Thema zu kommen: das ganz geht ein bisschen in Richtung XY-Problem, daher einfach mal die Frage: welches Problem möchtest du mit regulären Ausdrücken lösen?

Nur aus Texten der Form "<direction> <pair> <zahl>" (wobei die drei in beliebiger Reihenfolge stehen können), die drei jeweiligen Werte bekommen?
 
Mal als Gedanke - Schreib mal auf, was du eigentlich fachlich erkennen willst. Und gieße das in einen Algorithmus. Dann ist es vielleicht nicht 1 oder 3 RegEx-Ausdrücke sondern vielleicht 5+ mit insgesamt 10-50 Zeilen Code. Dafür ist es aber näher an der fachlichen Beschreibung damit auch deutlich verständlicher
 
Alles was dahinter kommt kann man üblicherweise ignorieren, grad wenn es darum geht, ob irgendwas richtig ist, sind LLMs absolut ungeeignet.


Um mal zum Thema zu kommen: das ganz geht ein bisschen in Richtung XY-Problem, daher einfach mal die Frage: welches Problem möchtest du mit regulären Ausdrücken lösen?

Nur aus Texten der Form "<direction> <pair> <zahl>" (wobei die drei in beliebiger Reihenfolge stehen können), die drei jeweiligen Werte bekommen?

konkret:
Aus
Code:
Sell BTC.USD 41300

TP 1 41200

TP 2 41100

SL 41600

in Form von named captured groups
das "Sell" rausziehen (kann auch stattdessen "buy" dastehen)
das "Btc.Usd" rausziehen (kann auch statt .ein / dastehen oder auch gar nichts zwischen den 2 währungen)
die zahl am ende der 1. zeile (nennen wir sie "entry").

in den folgezeilen die zahlen rausziehen und sie mit dem ausdruck davor benennen (also ne "tp 1" "tp2" "sl" variable, die die jeweilige zahl beinhaltet.
wobei ein tp2 mit zahl nicht zwingend vorkommen muss.

und in zeile 1 können die 3 infos eben in beliebier reihenfolge vorkommen.

kann also auch als
Code:
 BTC.USD 41300 Sell

TP 1 41200

TP 2 41100

SL 41600

auftauchen

sind halt nachrichten was für einen forextrade man amchen soll, mit take profit 1 und 2, stop loss, richtung, paar und eisntiegspunkt (die zahl in zeile 1).

will halt alle relevanten infos rausziehen und idealerweise automatisch passend benannten variabeln zuordnen mit denen ich weiterarbeiten kann.

denke, da sollte an und für sich regex am bestern dafür geeignet sein.
 
Ich würde es wie folgt lösen:
  • Zeile 1 an Trennzeichen (Space/Tabulator) splitten
  • jedes gesplitte Element bewerten, was es ist (Buy/Sell per String vergleich, Die Wert per StringUtils.isNumeric, das dritte per RegEx)
  • Die weiteren Zeilen jeweils per RegEx auswerten.
 
konkret:
Aus
Code:
Code:
Sell BTC.USD 41300

TP 1 41200

TP 2 41100

SL 41600

in Form von named captured groups
das "Sell" rausziehen (kann auch stattdessen "buy" dastehen)
das "Btc.Usd" rausziehen (kann auch statt .ein / dastehen oder auch gar nichts zwischen den 2 währungen)
die zahl am ende der 1. zeile (nennen wir sie "entry").

in den folgezeilen die zahlen rausziehen und sie mit dem ausdruck davor benennen (also ne "tp 1" "tp2" "sl" variable, die die jeweilige zahl beinhaltet.
wobei ein tp2 mit zahl nicht zwingend vorkommen muss.

und in zeile 1 können die 3 infos eben in beliebier reihenfolge vorkommen.

Man kann das vielleicht mit diesem Ausdruck machen (hier als Beispiel auf regex101):
Code:
(?<header>(((?<direction>Sell|Buy)|(?<pair>[A-Z]{3}\.[A-Z]{3})|(?<entry>\d{5}))\s+){3})\n*TP 1 (?<TP1>\d{5})\n*(TP 2 (?<TP2>\d{5}))?\n*SL (?<SL>\d{5})
Der ist aber nicht perfekt. Z.B. erlaubt er im header zwar eine beliebige Reihenfolge von direction, pair und entry, stellt aber nicht sicher, dass es jeweils genau ein Element davon gibt. Es wären beispielsweise auch zwei direction, ein pair und kein entry erlaubt. Vielleicht lässt sich das mit Lookaround-Assertions noch verbessern, aber ich bezweifle, dass sich das lohnt, denn der Regex würde deutlich häßlicher werden.
 

Zurück
Oben