2017-05-22 2 views
2

Ich bin auf einem regulären Ausdruck fest:Regex und Bilanzkreise

ich eine Eingabezeichenfolge mit Zahlen und einem Buchstaben, die mehr Zahlen und Buchstaben innerhalb der Zeichenfolge und zwischen Klammern enthalten:

Nur einige Beispiele

26U(35O40) will be read as 26 and (35 or 40) 
22X(34U(42O27)) will be read as 22 xor (34 and (42 or 27)) 
21O(24U27) will be read as 21 or (24 and 27) 
20X10X15 Will be read as 20 xor 10 xor 15 

ich gelesen habe, dass diese unter Verwendung von Bilanzkreisen erhalten werden können, jedoch habe ich versucht, viele reguläre Ausdrücke und schließt die folgenden:

Ich habe auch gedacht, dass ich es vielleicht härter mache und ich sollte einfach mehrmals die gleiche Regex laufen lassen, erstmalig für alles außerhalb der Klammer und das zweite Mal für die inneren Sachen und es nochmal ausführen wenn die übereinstimmt innere. Etwas wie das:

(?<ConditionId>\d+)?(?<Operator>U|O|X)?(?<Inner>(?:\().*(?:\))) 

Vorschläge oder Hilfe?

Vielen Dank im Voraus.

Edit 1: Ich muss die Eingabe nicht validieren, nur parse es.

Edit 2: Der Grund dafür ist, eine Bedingung durch die Bedingung Id zu identifizieren und dann den Operator gegen die anderen Bedingungen in der Eingabe String anzuwenden. In der gleichen Reihenfolge, wie sie in der Eingabezeichenfolge angezeigt wird, wäre ein allgemeines Beispiel zum besseren Verständnis logische Gatter:

Für eine gegebene Eingabe von 20x10x15 muss ich die Bedingungen durch die BedingungId identifizieren und prüfen, ob Bedingung ist gültig und gilt den XOR-Operator auf sie, so etwas wie:

true X true X false = false; 
false X false X true = true; 
true X (false U true) = true 

das ist der Grund, warum ich kann nicht alle Gruppe in eine „ConditionId“ -Gruppe und „Operator“ Gruppe.

bearbeiten 3 Dies ist auch ein gültiges Beispiel

(23X10)U(30O(20X19) 
+1

Warum haben Sie sich auf Regex für die Lösung dieses speziellen Problems entschieden? Sie sollten in der Lage sein, einen Parser mit regulären String-Operationen und einem Stack zu schreiben. – willaien

+0

Hallo, danke für den Vorschlag, ich kam mit Regex, weil die Bedingungen tatsächlich ein bisschen komplizierter sind als die, die ich für das Beispiel verwendet habe, und ich dachte, der richtige Weg wäre Regex, denn manchmal ist das Schwierigste das Einfachste und ich wollte nicht mit String-Operationen kämpfen (das kann manchmal auch schwieriger sein). Wie auch immer, Sie haben recht und ich werde auf jeden Fall einen Blick darauf werfen, wenn ich das Problem mit der Regex nicht lösen kann, da es meine zweite Option war. – Nekeniehl

+1

Müssen Sie eigentlich * ersetzen *? Nicht nur * Teile * der Strings extrahieren? '" 22X (34U (42O27)) "=>' "22 xor (34 und (42 oder 27))" ' –

Antwort

0

Wenn Sie (\d+[A-Z]*[()]?)+ verwenden es ein Spiel auf 22X(34U(42O27)) mit diesen Aufnahmen auf Groups[1].Captures

22X( 34U( 42O zurückkehren und 27)

Das gibt genug Informationen, um den Code zu verarbeiten.

Auf 20X10X15 die gleiche Capture-Gruppe

20X10X und 15

0

Angenommen, Ihre Eingabe gibt, ist bereits gültig, und Sie wollen es zu analysieren, hier ist eine ziemlich einfache regex zu erreichen, dass :

(?: 
    (?<ConditionId>\d+) 
    | 
    (?<Operator>[XUO]) 
    | 
    (?<Open>\() 
    | 
    (?<Group-Open>\)) 
)+ 

Working example - Regex Storm - Wechseln Sie zur Registerkarte Tabelle, um alle Erfassungen anzuzeigen.

Das Muster erfasst:

  • Zahlen in die $ConditionId Gruppe.
  • Operatoren in die $Operator Gruppe.
  • Unter Ausdrücke in Klammern in die $Group Gruppe (braucht einen besseren Namen?). Für die Zeichenfolge 22X(34U(42O27)) werden beispielsweise zwei Erfassungen vorgenommen: 42O27 und 34U(42O27).

Jede capture enthält die Position der Übereinstimmungszeichenfolge. Die Beziehungen zwischen $Group und seinen $Operator s, $ConditionId s und sub $Group s werden nur unter Verwendung dieser Positionen ausgedrückt.

Die (?<Group-Open>) Syntax wird verwendet, wenn wir eine schließende Klammer zu Capture alles seit der entsprechenden öffnenden Klammer erreichen. Dies wird hier genauer erklärt: What are regular expression Balancing Groups?

+0

Hallo, Danke für die detaillierte Antwort, aber das habe ich zuerst erfolgreich versucht, das Problem ist, dass alles später gemischt wird .. Der Grund, warum ich die Bedingungen oder die Operatoren nicht gruppieren kann, ist, weil ich später die Bedingungen anhand der Id identifizieren muss und wenden Sie den Operator gegen die anderen Bedingungen in der gleichen Weise wie in der Eingabe an. – Nekeniehl