Oprócz @ Revo answer: nie tylko warunkowego konstruktu
z wyraźnym zerowej szerokości twierdzenia jako jego wypowiedzi są naruszone. W rzeczywistości dotyczy to prawie wszystkich konstruktów warunkowych, w których wyrażenia warunkowe są wyokrąglane regexy (grupowanie, warunkowe, inne specjalne) używane bez dodatkowego nawiasu.
Istnieją cztery rodzaje (MIS) zachowania w takich przypadkach: grupa tablica
przechwytywania zostaje zniekształcone (jak wskazano przez OP), a mianowicie grupa przechwytywania bezpośrednio po konstrukt warunkowego jest stracone pozostałe grupy są przesunięte w lewo, pozostawiając niezdefiniowaną ostatnią grupę przechwytywania.
W poniższych przykładach oczekiwany przydział przechwytywania
$1="a", $2="b", $3="c"
natomiast rzeczywisty wynik jest
$1="a", $2="c", $3="" (the latter is empty string)
Dotyczy:
Zgłasza ArgumentException
w czasie wykonywania, gdy regex jest analizowany. Ma to sens, ponieważ wyraźnie ostrzega nas przed potencjalnym błędem regularnego użycia, zamiast grać zabawne sztuczki z chwytaniem, jak w poprzednim przypadku.
Dotyczy:
(a)(?(?<n>.))(b) (c)
, (a)(?(?'n'.))(b) (c)
- Komunikat wyjątku - nazwanych grup: "Alternation conditions do not capture and cannot be named"
(a)(?(?'-n' .))(b) (c)
, (?<a>a)(?(?<a-n>.))(b) (c)
- grupy bilansujące - Komunikat wyjątku: "Alternation conditions do not capture and cannot be named"
(a)(?(?# comment))(b) (c)
- inline komentarz - Komunikat wyjątku: "Alternation conditions cannot be comments"
Zgłasza OutOfMemoryException
podczas dopasowywania wzorca. To jest oczywiście błąd, jak sądzę.
Dotyczy:
(a)(?(?i))(b) (c)
- opcji inline (nie mylić z opcji grupowych)
[Zaskakująco] działa zgodnie z oczekiwaniami, ale jest to raczej zbyt sztuczny przykład:
Wszystkie powyższe wyrażenia można ustalić, zamykając wyrażenie warunku na jawny nawias (tj. dodatkowe, jeśli samo wyrażenie zawiera już nawiasy). Oto trwałe wersje (w kolejności występowania): Kod
(a)(?((?=.)))(b) (c)
(a)(?((?!z)))(b) (c)
(a)(?((?<=.)))(b) (c)
(a)(?((?<!)))(b) (c)
(a)(?((?:)))(b) (c)
(a)(?((?i:.)))(b) (c)
(a)(?((?>.)))(b) (c)
(a)(?((?(1).)))(b) (c)
((?<n>a))(?((?(n).)))(b)(c)
(a)(?((?(?:.).)))(b) (c)
(a)(?((?<n>.)))(b) (c)
(a)(?((?'n'.)))(b) (c)
(a)(?((?'-n' .)))(b) (c)
(?<a>a)(?((?<a-n>.)))(b) (c)
(a)(?((?# comment)))(b) (c)
(a)(?((?i)))(b) (c)
(a)(?((?(.).)))(b) (c)
próbki, aby sprawdzić wszystkie te wyrażenia: (?()) https://ideone.com/KHbqMI
DOTYCZĄCE 'a b (c)', trzeba pamiętać, że ' (?()) 'jest równe' (? (? =)) ', a nie' (? (?
Tak, dodano poprawną frazę. @ WiktorStribiżew – revo
Innym sposobem obejścia tego problemu jest zamknięcie warunku w dodatkowej grupie przechwytującej: 'a (? ((?