php - preg_replace 去除前导斜线

标签 php regex

我想从 URL 中去除前导斜杠和查询字符串,但不知道如何同时进行。我有这段代码非常适合剥离查询字符串,但它留下了前导斜杠

preg_replace('/\?.*$/', '', $_SERVER['REQUEST_URI'])

如果我的 URL 是 www.mysite.com/myPage?querystring=123,上面的内容会留下 /myPage。我该如何调整它以便我也可以删除前导斜线?

另外,你能给我指出一个资源来帮助我理解 preg_replace 模式匹配吗?

最佳答案

在这种简单的情况下,我可能更喜欢 PHP 的简单字符串函数而不是正则表达式:

$addr  = ltrim($_SERVER['REQUEST_URI'], '/'); // zap a leading slash
$q_pos = strpos($addr, '?'); // get the string position of a '?'
$addr  = $q_pos !== FALSE ? substr($addr, 0, $q_pos) : $addr; // pull out URI

PHP 的 strpos() docs返回一个整数值,所以有可能 $q_pos === 0 ...这就是我们检查 $q_pos !== FALSE 的原因.

更新

我想我应该回答这个问题,但是......所以在这种情况下实际使用正则表达式......

$address = '/test/url/test.php?extra';
$pattern = '{^/?([^\?]+)\?.*$}';
$replace = '$1';
$address = preg_replace($pattern, $replace, $address);
echo "$address"; // outputs: test/url/test.php

这是如何运作的?好吧……我们的模式指定了一个捕获组 ([^\?]+)optional 正斜杠 /? 之后使用括号获取所有内容直到第一次出现可选 \?在字符串中。请注意,我们使用反斜杠转义实际的问号字符,因为它在正则表达式模式的上下文中有意义。正则表达式模式的最后部分 .*简单地将零个或多个字符匹配到字符串的末尾。

最后,我们的替换简单地指定了 $1引用我们用原始括号分组 ([^\?]+) 捕获的文本.

另一件需要注意的事情是,正则表达式新手通常没有意识到,您不是必须使用 / 的。作为模式分隔符。在这种情况下,我们要匹配实际的正斜杠字符,我会使用其他东西(例如花括号)。

我通常将正则表达式初学者指向 this link帮助他们开始。

更新 2

上面的正则表达式假设总是有一个查询字符串,所以如果您遇到一个没有查询字符串的 URI(例如,/All-Products),该正则表达式将不起作用。为了解决这个问题,只需更改您的模式以使查询字符串可选:

$pattern = '{^/?([^\?]+)(?:\?.*)?$}'; // use an optional non-capturing group

-或-

$pattern = '{^/?([^\?]+)\??.*$}'; // make the escaped ? optional

关于php - preg_replace 去除前导斜线,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8731715/

相关文章:

python - 将 C 中的包含文件转换为 python

javascript - 正则表达式 - 检查 url 没有扩展名

php - mysql 日期格式与 php

php - 输入错误网址时重定向到404页面

JavaScript 正则表达式 - 检查数字匹配的数量

java - 为什么 String.matches 在 Java 中返回 false?

php - preg_replace_callback 在参数 2 处调用 $this->method ('\\1' )

php - 无法更新单个 Composer 包

php - Laravel5.2 调度 :run don't work with cron job

javascript - 使用正则表达式解析 Javascript 中的 Wiki 标记