Какая поддержка существует для PCRE (Perl-совместимых регулярных выражений) на распространенных языках?

Меня интересуют возможности PCRE (совместимые с Perl регулярные выражения) и мне интересно, станут ли они де-факто подходом ко всем основным языкам (меня интересует Java). Я готов использовать библиотеку, если это необходимо.

Я также не смог найти хорошую страницу в SO, описывающую плюсы и минусы PCRE, поэтому, если ее не существует, было бы полезно включить это в ответы.

ИЗМЕНИТЬ Меня интересуют возможности, выходящие за рамки регулярных выражений Java 1.6, особенно именованные группы захвата.


person peter.murray.rust    schedule 19.09.2009    source источник


Ответы (5)


Кажется, что больше основных языков на самом деле используют свою собственную реализацию «Perl-подобных» регулярных выражений, чем фактически используют libpcre. Языки, попадающие в этот класс, включают (как минимум) Java, JavaScript и Python.

Библиотека Java java.util.regex использует синтаксис, который в значительной степени основан на регулярных выражениях Perl (приблизительно версии 5.8), включая правила экранирования, классы \p и \P Unicode, нежадные и "притяжательные" квантификаторы, обратные ссылки, \Q..\E цитирование, и несколько конструкций (?...), включая группы без захвата, группы просмотра вперед/назад с нулевой шириной и группы без возврата. На самом деле регулярные выражения Java имеют больше общего с регулярными выражениями Perl, чем libpcre. :)

Язык JavaScript также использует регулярные выражения, производные от Perl; Классы Unicode, просмотр назад, притяжательные квантификаторы и группы без возврата отсутствуют, но все остальное, что я упомянул для Java, также присутствует в JS.

Синтаксис регулярных выражений Python также основан на Perl 5, с нежадными квантификаторами, большинством конструкций (?...), включая незахватывающие группы, упреждающий/обратный и условный шаблоны, а также именованные группы захвата (но с другим синтаксисом, чем любой из них). Perl или PCRE). Группы без возврата и «притяжательные» квантификаторы (насколько я вижу) отсутствуют, как и классы символов Unicode \p и \P, хотя стандартные классы \d, \s и \w поддерживают Unicode, если это требуется.

person hobbs    schedule 19.09.2009
comment
Спасибо. Я уточнил свой вопрос, чтобы показать, что меня интересуют функции, которые не поддерживает Java 1.6. - person peter.murray.rust; 19.09.2009
comment
Perl, Python, .NET, libpcre. Это единственные известные мне реализации, поддерживающие именованные группы захвата. - person hobbs; 19.09.2009
comment
На самом деле многие расширения Python будут работать на современном Perl. - person Brad Gilbert; 21.02.2013

Это старый вопрос, но для его обновления в Java 7 добавлены именованные группы захвата.

person Stephen Smith    schedule 25.08.2020

Мне ... интересно, станут ли они [PCRE] де-факто подходом во всех основных языках (меня интересует Java).

Это требует предположений, но я думаю, что ответ - Нет... в случае с Java. Я основываюсь на том факте, что не смог найти никакой стоящей реализации PCRE для Java.

Если бы существовала реальная потребность/спрос на PCRE в Java, я бы ожидал, что будет больше библиотек.


ОБНОВЛЕНИЕ

Поскольку я написал первоначальный ответ, все больше людей/групп реализовали библиотеки Java, которые предоставляют (или утверждают, что предоставляют) регулярные выражения, совместимые с PCRE.

И, очевидно, со временем команда разработчиков Java может добавить (и добавила) некоторые функции Perl к поддержке регулярных выражений в Java. Например, в Java 7 были добавлены именованные группы захвата.

Но полная совместимость с PCRE, похоже, не является первоочередной задачей для команды разработчиков Java. Например:

И учитывая, что полная совместимость, скорее всего, нарушила бы подмножество существующих Java-приложений, я все же думаю, что ответ — нет.

person Stephen C    schedule 06.08.2013

Попробуйте разделить этот матч:

(?:
  (?:'[\S\s]*?(?<!\\)') # Consume characters inside of a quoted string
  |(?:\/\*[\S\s]*?\*\/) # Consume multi-line comments
  |(?m:\/{2}[^\n]*$\n)  # Consume single-line comments
)(*SKIP)(*F)            # Fail match if any of the previous matches were found
|(?<=;)                 # Capture position right after semicolon

Обязательно используйте модификаторы «x» и «g» (при необходимости).

Пример

person Erutan409    schedule 11.08.2015
comment
Вы можете добавить флаг /x внутри re, начав его с (?x: - person shawnhcorey; 05.08.2016

Это очень похоже на вопрос «Является ли Х единственным верным путем!?» типа вопрос. PCRE имеет много недостатков, наиболее очевидными из которых являются его сложность и сомнительная полезность. Редко существует единственный верный способ для чего-либо, и в области библиотек регулярных выражений PCRE, безусловно, таковым не является.

На мой взгляд, регулярные выражения Perl — это полный мусор. Как только вы выйдете далеко за пределы набора функций, предлагаемых расширенными регулярными выражениями POSIX (ERE), вы также можете использовать что-то вроде реализации PEG. Единственная причина, по которой PCRE используется так широко, заключается в том, что людям легко решить проблему, просто подключившись к библиотеке.

person R. T.    schedule 12.12.2013