Ein Regex wie (?:(?=abc)|[abc])+
entspricht einem String, der aus a
, b
und c
besteht, bis die Lookahead-Bedingung erfüllt ist. Zum Beispiel für die Zeichenfolge acbababcaaa
wird es übereinstimmen acbab
- Stoppen direkt vor der ersten abc
, obwohl es bis zum Ende der Zeichenfolge vorrücken könnte, wenn es übermäßig gierig wäre.Lookahead-Verhalten in wiederholter Alternationsgruppe
Wir können dies erzwingen, indem wir $
an das Ende des Musters ((?:(?=abc)|[abc])+$
) hinzufügen - jetzt stimmt es tatsächlich mit dem Ende der Zeichenfolge überein.
Wenn wir jetzt die Wiederholung zu posesive ((?:(?=abc)|[abc])++$
) ändern - es wird bcaaa
- also die erste Position, wo der Lookahead nicht mehr übereinstimmen kann.
Kann jemand die Gründe für diese Verhaltensweisen erklären?
Die erste entspricht nur dem Beginn der Zeichenfolge, wenn kein globaler Suchmodus verwendet wird (siehe [demo] (https://regex101.com/r/t9zDtJ/1)), nicht 'abcab'. –
@ WiktorStribiżew Sie sind offensichtlich richtig - ich hatte die falsche Zeichenfolge in Kopie + einfügen. Die Frage wurde aktualisiert. –
Der Punkt hier glaube ich ist, dass in PCRE der Index nicht bewegt, wenn Sie eine * Null-Breite * haben. Beachten Sie, dass das Verhalten in JS anders ist, da JS-Regex den Regex-Index-Fortschritt nach einer Null-Breite-Übereinstimmung erzwingt. In einigen Situationen ist dieses Verhalten groß (wenn Sie aufeinanderfolgende Zero-Width- und Non-Zero-Width-Teilstrings abgleichen und - wie in diesem Fall - "Glitches" sein können. Im letzten Beispiel benötigt der Possessive-Quantor das Ende der Zeichenfolge direkt nach der Verzweigung übereinstimmt, so dass alle Null-Breite Übereinstimmungen die Übereinstimmung fehlschlagen, und Sie nur den letzten Chunk mit keine 'abc 'erhalten –