Я нашел его в следующем регулярном выражении:
\[(?:[^][]|(?R))*\]
Он соответствует квадратным скобкам (с их содержимым) вместе с вложенными квадратными скобками.
Я нашел его в следующем регулярном выражении:
\[(?:[^][]|(?R))*\]
Он соответствует квадратным скобкам (с их содержимым) вместе с вложенными квадратными скобками.
[^][] - это класс символов, который означает все символы, кроме [ и ].
Вы можете избежать экранирования специальных символов [ и ], поскольку это не является двусмысленным для PCRE, механизма регулярных выражений, используемого в preg_.
Так как [^] неверно в PCRE, единственный способ для синтаксического анализа регулярных выражений состоит в том, что ] находится внутри класса символов, который будет закрыт позже. То же самое с [. Он не может повторно открыть класс символов (кроме символьного класса POSIX [:alnum:]) внутри класса символов. Тогда последний ] понятен; это конец класса символов. Однако a [ вне класса символов должен быть экранирован, так как он анализируется как начало класса символов.
Таким же образом вы можете написать []] или [[] или [^[] без экранирования [ или ] в классе символов.
Вы можете использовать этот синтаксис с несколькими регулярными выражениями: PCRE (PHP, R), Perl, Python, Java,.NET, GO, awk, Tcl (если вы разделите свой рисунок фигурными скобками, спасибо Donal Fellows)...
Но не с: Ruby, JavaScript (кроме IE < 9),...
Как отмечал m.buettner, [^]] не является двусмысленным, поскольку ] является символом first, [^a]] рассматривается как все, что не является a, за которым следует ]. Чтобы иметь a и ], вы должны написать: [^a\]] или [^]a]
В частном случае JavaScript спецификация позволяет [] как токен регулярного выражения, который никогда не совпадает (другими словами, [] всегда терпит неудачу) и [^] как регулярное выражение, которое соответствует любому символу. Тогда [^]] рассматривается как любой символ, за которым следует a ]. Фактическая реализация меняется, но современный браузер обычно придерживается определения в спецификации.
Сведения о шаблоне:
\[ # literal [
(?: # open a non capturing group
[^][] # a character that is not a ] or a [
| # OR
(?R) # the whole pattern (here is the recursion)
)* # repeat zero or more time
\] # a literal ]
В вашем примере шаблона вам не нужно избегать последнего ]
Но вы можете сделать то же самое с этим шаблоном, немного оптимизированным, и более полезную причину можно использовать повторно как подшаблон (с (?-1)): (\[(?:[^][]+|(?-1))*+])
( # open the capturing group
\[ # a literal [
(?: # open a non-capturing group
[^][]+ # all characters but ] or [ one or more time
| # OR
(?-1) # the last opened capturing group (recursion)
# (the capture group where you are)
)*+ # repeat the group zero or more time (possessive)
] # literal ] (no need to escape)
) # close the capturing group
или лучше: (\[[^][]*(?:(?-1)[^][]*)*+]), что позволяет избежать затрат на чередование.