Перевести Perl регулярные выражения в .NET - PullRequest
19 голосов
/ 05 августа 2010

У меня есть несколько полезных регулярных выражений в Perl. Есть ли простой способ перевести их на диалект регулярных выражений .NET?

Если нет, есть ли краткая справка о различиях?

Ответы [ 3 ]

33 голосов
/ 05 августа 2010

Существует большая таблица сравнения в http://www.regular -expressions.info / refflavors.html .


Большинство основных элементов одинаковы, различия:

Незначительные различия:

  • escape-последовательности Юникода. В .NET это \u200A, в Perl это \x{200A}.
  • \v в .NET - это просто вертикальная табуляция (U + 000B), в Perl - класс «вертикальные пробелы». Конечно, из-за этого в Perl есть \V.
  • Условное выражение для именованной ссылки в .NET: (?(name)yes|no), но (?(<name>)yes|no) в Perl.

Некоторые элементы доступны только для Perl:

  • Посессивные квантификаторы (x?+, x*+, x++ и т. Д.). Вместо этого используйте невыражающее подвыражение ((?>…)).
  • Именованная escape-последовательность Юникода \N{LATIN SMALL LETTER X}, \N{U+200A}.
  • Чехол складной и убегающий
    • \l (следующий символ в нижнем регистре), \u (следующий символ в верхнем регистре).
    • \L (строчные буквы), \U (прописные буквы), \Q (кавычки метасимволов) до \E.
  • Сокращенная запись свойства Unicode \pL и \PL. Вы должны включить скобки в .NET, например \p{L}.
  • Странные вещи, такие как \X, \C.
  • Специальные классы символов, такие как \v, \V, \h, \H, \N, \R
  • Ссылка на конкретную или предыдущую группу \g1, \g{-1}. Вы можете использовать только абсолютный групповой индекс в .NET.
  • Именованная обратная ссылка \g{name}. Вместо этого используйте \k<name>.
  • Класс символов POSIX [[:alpha:]].
  • Шаблон сброса ветви (?|…)
  • \K. Используйте взамен ((?<=…)) взамен.
  • Утверждение оценки кода (?{…}), подвыраженное подвыражение (??{…}).
  • Ссылка на выражение экспрессии (рекурсивный шаблон) (?0), (?R), (?1), (?-1), (?+1), (?&name).
  • Некоторые предикаты условного выражения являются специфичными для Perl:
    • код (?{…})
    • рекурсивный (R), (R1), (R&name)
    • определить (DEFINE).
  • Специальные глаголы управления возвратом (*VERB:ARG)
  • Синтаксис Python
    • (?P<name>…). Вместо этого используйте (?<name>…).
    • (?P=name). Вместо этого используйте \k<name>.
    • (?P>name). Нет аналога в .NET.

Некоторые элементы доступны только для .NET:

  • Задержка переменной длины. В Perl для позитивного просмотра используйте \K.
  • Произвольное регулярное выражение в условном выражении (?(pattern)yes|no).
  • Вычитание класса символов (недокументированное?) [a-z-[d-w]]
  • Балансировочная группа (?<-name>…). Это можно смоделировать с помощью утверждения оценки кода (?{…}), за которым следует (?&name).

Ссылки

2 голосов
/ 05 августа 2010

Они были разработаны для совместимости с регулярными выражениями Perl 5. Таким образом, регулярные выражения Perl 5 должны просто работать в .NET.

Вы можете перевести некоторые RegexOptions следующим образом:

[Flags]
public enum RegexOptions
{
  Compiled = 8,
  CultureInvariant = 0x200,
  ECMAScript = 0x100,
  ExplicitCapture = 4,
  IgnoreCase = 1,                 // i in Perl
  IgnorePatternWhitespace = 0x20, // x in Perl
  Multiline = 2,                  // m in Perl
  None = 0,
  RightToLeft = 0x40,
  Singleline = 0x10               // s in Perl
}

Другой совет - использовать дословные строки, чтобы вам не нужно было экранировать все эти escape-символы в C #:

string badOnTheEyesRx    = "\\d{4}/\\d{2}/\\d{2}";
string easierOnTheEyesRx = @"\d{4}/\d{2}/\d{2}";
1 голос
/ 05 августа 2010

Это действительно зависит от сложности регулярного выражения - многие из них будут работать одинаково из коробки.

Взгляните на эту .NET таблицу с регулярными выражениями, чтобы увидеть, делает ли оператор то, что вы ожидаете.

Я не знаю ни одного инструмента, который автоматически переводил бы между диалектами RegEx.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...