В этом случае ?
фактически используется в связи с :
. Сочетание ?:
в начале группировки означает группирование, но не захватывание текста / шаблона в скобках (например, он не будет сохранен ни в каких обратных ссылках, таких как \1
или $1
, поэтому вы не будете иметь возможность прямого доступа к сгруппированному тексту).
В частности, ?
имеет три различных значения в регулярном выражении:
Квантор ?
означает «ноль или одно повторение» выражения. Один из канонических примеров, которые я видел, это s?he
, который будет соответствовать she
и he
, поскольку ?
делает s
"необязательным"
Когда за квантификатором (+
, *
, ?
или общим {n,m}
) следует ?
, тогда совпадение не является жадным (т. Е. Оно будет соответствовать наименьшему строка, начинающаяся с той позиции, которая позволяет продолжить матч)
A ?
в начале группы в скобках означает, что вы хотите выполнить специальное действие. Как и в этом случае, :
означает группирование, но не захват. Точный список доступных действий будет несколько отличаться от одного механизма регулярных выражений к другому, но вот список (не обязательно всеобъемлющий) некоторых из них:
A. Группа без захвата : (?:text)
B. Lookaround : (?=a)
для прогнозирования, ?!
для негативного прогнозирования или ?<=
и ?<!
для прогнозирования (положительный и отрицательный соответственно).
C. Условные совпадения : (?(condition)then|else)
.
D. Атомная группировка : a(?>bc|b)c
(соответствует abcc
, но не abc
; см. Ссылку)
E. Встроенное включение / отключение модификаторов соответствия регулярному выражению : ?i
для включения режима, ?-i
для отключения. Вы также можете включать / отключать более одного модификатора одновременно, просто объединяя их, например, ?im
(i
не чувствителен к регистру и m
является многострочным).
F. Именованные группы захвата : (?P<name>pattern)
, на которые впоследствии можно ссылаться с помощью (?P=name)
. Механизм регулярных выражений .NET использует синтаксис (?<name>pattern)
.
Г. Комментарии : (?#Comment text)
. Лично я думаю, что это только добавляет беспорядок, но я думаю, что это могло бы послужить некоторому использованию ... Режим свободного пробега может быть лучшим вариантом (модификатор (?x)
).
Так что, по сути, цель ?
является просто контекстной. Если вы хотите ноль или более повторений буквального символа (
, вам нужно будет использовать \(?
, чтобы избежать парен.