Плохо выполняемое регулярное выражение - PullRequest
2 голосов
/ 22 апреля 2010

У меня очень плохо работает регулярное выражение, в настоящее время он заставляет Firefox, Chrome и IE зависать на некоторое время.

Вот рег-экс:

 ^([a-zA-Z0-9]+[/]?)+[a-zA-Z0-9]+$

Это вид сопоставления URL, но он должен соответствовать только запрошенному пути (не начиная с косой черты и не заканчивая ее).

Допустимые примеры:

  • Сегмент
  • Сегмент / Segment
  • сегмент / сегмент / сегмент (и т. Д.)

Неверные примеры:

  • / Сегмент
  • Сегмент /
  • Сегмент / Сегмент /

Использование приведенного выше регулярного выражения во всех трех браузерах и использование двух или более слешей приводит к зависанию браузеров.

Это, очевидно, плохо сформированный рег-экс, но кто-нибудь может помочь построить лучший?

Спасибо,

Ответы [ 3 ]

7 голосов
/ 22 апреля 2010

Лучше бы быть более детерминированным и без захвата групп:

^[a-zA-Z0-9]+(?:/[a-zA-Z0-9]+)*$

Таким образом, у вас нет перекрывающихся групп и вы не снимаете вещи без необходимости.

3 голосов
/ 22 апреля 2010

Думаю, проблема в том, что с необязательными строками / можно анализировать слишком много способов, в частности, любая последовательность из N алфавитов может быть сопоставлена ​​N-1 способами. Как насчет:

^([a-zA-Z0-9]+[/])*[a-zA-Z0-9]+$

т.е. 0 или более (1+ буквенно-косая черта) и одна последняя помощь (1+ буквенно-цифровых символов). (Конечно, как уже упоминалось в других ответах, вы можете также поставить ?: сразу после открытого парена, если вы хотите, чтобы группа не захватывала).

2 голосов
/ 22 апреля 2010

Попробуйте

^(?:[^/]+/)*[^/]+$

Или, если [a-zA-Z0-9]+ действительно необходимо, попробуйте

^(?:[a-zA-Z0-9]+/)*[a-zA-Z0-9]+$

Я лично считаю, что сначала все должно быть быстрее, хотя

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