Снова вопрос о регулярных выражениях! - PullRequest
0 голосов
/ 11 февраля 2010

Я действительно не знаю, в чем моя проблема в последнее время, но Регекс, кажется, доставляет мне больше всего хлопот.

Очень простая вещь, которую мне нужно сделать, но, похоже, не могу ее получить:

У меня есть URI, который возвращает либо / xmlfeed, либо / xmlfeed / what / is / this

Я хочу сопоставить / xmlfeed в любом случае.

Я пробовал много вариантов из следующего:

preg_match('/(\/.*?)\/?/', $_SERVER['REQUEST_URI'], $match);

Я бы прочитал это так: Матч вперед и затем совпадение с любым символом, пока не дойдет до необязательного слеша.

Ответы [ 6 ]

2 голосов
/ 11 февраля 2010

Почему бы и нет:

preg_match ('#/[^/]+#', _SERVER['REQUEST_URI'], $match);

$match[0] даст вам то, что вам нужно

2 голосов
/ 11 февраля 2010

зачем тебе регулярное выражение, которое тебя смущает ??

$string = "/xmlfeed/what/is/this";
$s = explode("/",$string,3);
print "/".$s[1]."\n";

выход

$ php test.php
/xmlfeed
1 голос
/ 11 февраля 2010

Ваша проблема - неохотный квантификатор. После того, как начальный слеш совпадает, .*? потребляет минимальное количество символов, которое ему разрешено, что равно нулю. Тогда /? вступает во владение; он не видит косую черту в следующей позиции (которая сразу после первой косой черты), но это нормально, потому что это необязательно. Результат: регулярное выражение всегда соответствует одной косой черте, а группа # 1 всегда соответствует пустой строке.

Очевидно, вы не можете просто заменить неохотный квантификатор на жадный. Но если вы замените .* чем-то, что не может сравниться с косой чертой, вам не придется беспокоиться о жадности. Это то, что делает K Prime , '#/[^/]+#'. Обратите также внимание на то, как он использует # в качестве разделителя регулярных выражений и избегает необходимости избегать косых черт внутри регулярного выражения.

1 голос
/ 11 февраля 2010

В PHP: '/(\/.*?)\/?/' - строка, содержащая регулярное выражение.

Сначала вы должны декодировать строку: /(/.*?)\/?/

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

Итак, чтобы это заработало:

  • Не забудьте экранировать символы со специальным значением в строках и регулярные выражения
  • Не путайте косую черту / с косой чертой \

Вы хотите сопоставить все после и после первого слеша, но перед любым (необязательным) вторым слешем (поэтому нам не нужен ?, который делает его нежадным):

/(\/[^\/]*)/

Который, выраженный в виде строки PHP:

'/(\\/([^\\/]*)/'
0 голосов
/ 11 февраля 2010

Используя опубликованные предложения, я попытался это сделать:

echo $_SERVER['REQUEST_URI'];
preg_match("/(\/.*)[^\/]/", $_SERVER['REQUEST_URI'], $match);
$url = "http://".$_SERVER['SERVER_NAME'].$match[0];
foreach($match as $k=>$v){
  echo "<h1>$k - $v</h1>";
}

Я тоже пробовал без. * И без скобок.

Без. * AND () возвращает / ТОЛЬКО со следующим символом.

Как это, он просто возвращает весь URI каждый раз

Таким образом, при запуске с кодом выше, вывод

/tea-time-blog/post/20 0 - /tea-time-blog/post/20 1 - /tea-time-blog/post/2

Кстати, этот код eval (). Я не думаю, что это должно повлиять на то, как PHP обрабатывает регулярное выражение.

0 голосов
/ 11 февраля 2010

Я знаю, что это позволяет избегать регулярных выражений и, следовательно, избегает вопроса, но как насчет разбиения URI (в слэше) на массив.

Тогда вы можете работать с элементами массива и игнорировать биты URI, которые вам не нужны.

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