Дальность не в порядке в символьном классе

Я получаю эту нечетную ошибку в функции preg_match():

Предупреждение: preg_match(): Ошибка компиляции: диапазон не соответствует порядку в классе символов со смещением 54

Линия, вызывающая это:

preg_match("/<!--GSM\sPER\sNUMBER\s-\s$gsmNumber\s-\sSTART-->(.*)<!--GSM\sPER\sNUMBER\s-\s$gsmNumber\s-\sEND-->/s", $fileData, $matches);

Что это такое регулярное выражение, это проанализировать HTML файл, извлекая только часть между:

<!--GSM PER NUMBER - 5550101 - START-->

и

<!--GSM PER NUMBER - 5550101 - END-->

Есть ли у вас намек на то, что может вызвать эту ошибку?

Ответы

Ответ 1

Если $gsmNumber содержит квадратную скобку, обратную косую черту или другие специальные символы, это может вызвать эту ошибку. Если это возможно, вы можете проверить это, чтобы убедиться, что на самом деле это число до этой точки.

Изменить 2016:

Существует функция PHP, которая может вызывать специальные символы внутри регулярных выражений: preg_quote().

Используйте его следующим образом:

preg_match(
  '/<!--GSM\sPER\sNUMBER\s-\s' .
  preg_quote($gsmNumber, '/') . '\s-\sSTART-->(.*)<!--GSM\sPER\sNUMBER\s-\s' .
  preg_quote($gsmNumber, '/') . '\s-\sEND-->/s', $fileData, $matches);

Очевидно, что в этом случае, поскольку вы использовали одну и ту же строку дважды, вы можете сначала назначить цитированную версию переменной и повторно использовать ее.

Ответ 2

Привет, я получил ту же ошибку и решил ее:

  Warning: preg_match(): Compilation failed: range out of order in character class at offset <N>

Этап исследования:

. Диапазон не соответствует порядку.. Таким образом, существует определенный диапазон, который нельзя использовать.

.. при смещении N.. Я быстро просмотрел свой шаблон регулярного выражения. Позиция N была "-" . Он использовал для определения диапазонов, таких как "a-z" или "0-9" и т.д.

Решение

Я просто избежал "-" .

 \-    

Теперь он интерпретируется как символ "-" , а не как диапазон!

Ответ 3

Эта ошибка вызвана неправильным диапазоном. Например: 9-0 a-Z Чтобы исправить это, вы должны изменить 9-0 на 0-9 и a-Z на a-zA-Z В вашем случае вы не избегаете символа "-", а затем preg_match пытается проанализировать регулярное выражение и сбой с неправильным диапазоном. Выбери "-", и он должен решить вашу проблему.

Ответ 4

Я получал эту ошибку со следующей последовательностью:

[/-.]

Простое перемещение . в начало фиксировало проблему:

[./-]

Ответ 5

В то время как другие ответы верны, я с удивлением вижу, что никто не предложил ускользнуть от переменной с помощью preg_quote(), прежде чем использовать ее в регулярном выражении. Поэтому, если вы хотите сопоставить фактическую скобку или что-то еще, что означает что-то в регулярном выражении, это будет преобразовано в литеральный токен:

$escaped = preg_quote($gsmNumber);
preg_match( '/<!--GSM\sPER\sNUMBER\s-\s'.$escaped.'\s-\sSTART-->(.*)<!--GSM\sPER\sNUMBER\s-\s'.$escaped.'\s-\sEND-->/s', $fileData, $matches);

Ответ 6

У вас, вероятно, есть люди, которые вставляют мобильные номера, включая символы +, -, (и/или), и просто используют их как есть в preg_match, поэтому вы можете захотеть дезинфицировать данные, предоставленные перед его использованием (то есть, сняв эти символы полностью).

Ответ 7

Это ошибка в нескольких версиях PHP, так как я только что проверил текущую версию 5.3.5, как упакованную с XAMPP 1.7.4 в домашней версии Windows XP.

Даже некоторые очень простые примеры демонстрируют проблему, например,

    $pattern = '/^[\w_-. ]+$/';
    $uid = 'guest';
    if (preg_match($pattern, $uid)) echo 
      ("<style> p { text-decoration:line-through } </style>");

Пользователи PHP знают об ошибке с 10.10.2010. См. http://pear.php.net/bugs/bug.php?id=18182. Ошибка отмечена как "закрытая", но сохраняется.