PHP正则前瞻排除字符问题:提取URL时slug末尾短横无法去除
解决正则提取slug末尾多余短横的问题
你的问题出在原正则对slug的匹配逻辑上:[a-z0-9\-]+会贪婪匹配所有包含字母、数字和短横的内容,包括ID前面的那个短横,而后面的(?<=\-)只是断言ID前有短横,并不会将这个短横从slug的匹配结果中排除。
修正后的正则方案
可以调整正则表达式,让slug匹配到最后一个短横之前的有效内容,确保它不会包含ID前的短横:
$url = "/cockpit/posts/my-second-article-2-155"; $routes = []; // 修改后的正则:slug匹配由字母数字和中间短横组成的内容,最后以字母数字结尾,然后接短横+ID $patterns = "/(?<controller>[a-z]+)\/(?<slug>[a-z0-9]+(?:-[a-z0-9]+)*)-(?<id>[0-9]+)/i"; preg_match($patterns, $url, $matches); foreach ($matches as $key => $value){ if(!is_numeric($key)){ $routes[$key] = $value; } } var_dump($routes);
匹配结果
执行后会得到期望的输出:
array(3) { ["controller"]=> string(5) "posts" ["slug"]=> string(19) "my-second-article-2" ["id"]=> string(3) "155" }
正则逻辑说明
(?<slug>[a-z0-9]+(?:-[a-z0-9]+)*):[a-z0-9]+:匹配开头的字母或数字(?:-[a-z0-9]+)*:非捕获组,匹配任意数量的“短横+字母/数字”组合,确保slug中的短横只会出现在内容中间,不会以短横结尾
-:明确匹配slug和ID之间的分隔短横(?<id>[0-9]+):匹配纯数字的ID部分
这种写法既能准确提取各部分内容,也能避免slug末尾出现多余的短横。
内容的提问来源于stack exchange,提问作者devitdc
相关产品推荐
相关产品推荐

