我正在尝试将不同的URL与我的控制器的MVC操作匹配。
这是我正在测试的当前表达式:
#^/products((/([0-9]+)-([0-9a-z\_]+))*(/(index\.(html|pdf|xml|json))?)?)?$#i
当我尝试将其与之匹配时:
/products/22-test/25-test2
我期望得到(通过preg_match_all)以下结果:
array(5) {
[0]=>
string(26) "/products/22-test/25-test2"
[1]=>
string(17) "/22-test"
[2]=>
string(2) "22"
[3]=>
string(5) "test"
[4]=>
string(17) "/25-test"
[5]=>
string(2) "25"
[6]=>
string(5) "test2"
}
但我得到了
array(5) {
[0]=>
string(26) "/products/22-test/25-test2"
[1]=>
string(17) "/22-test/25-test2"
[2]=>
string(9) "/25-test2"
[3]=>
string(2) "25"
[4]=>
string(5) "test2"
}
更新
问题在于我没有将类别列表翻译成单独的元素,只是为了让我的问题尽可能清楚......
我正在使用(/([0-9]+)-([0-9a-z\_]+))*
尝试将尽可能多的类别标识符转换为已解析的项目。这就是为什么我使用(...)*
,它应该允许任意数量的类别匹配并且应该匹配它们中没有?
更新2
似乎如果我更新regexp以支持多次相同的类别标识符,它会被解析,我希望(...)*
会多次解析它而不是给我一个大的类别标识符列表。< / p>
例如,这很好用:
#^/products((/([0-9]+)-([0-9a-z\_]+))?(/([0-9]+)-([0-9a-z\_]+))?(/([0-9]+)-([0-9a-z\_]+))?(/([0-9]+)-([0-9a-z\_]+))?(/([0-9]+)-([0-9a-z\_]+))?(/(index\.(html|pdf|xml|json))?)?)?$#i
但强迫我多次重复类别选择器。因此,如果我有一个客户决定在他的目录中放置超过X个类别,我被阻止,网址将无法正确解析...
有没有办法支持?
答案 0 :(得分:2)
结果是位置结果。即位置1捕获第一个()
,位置2捕获第二个()
。
*
使捕获组更大,但不会使位置成倍增加。
您可能希望在第二步中使用带有(/([0-9]+)-([0-9a-z\_]+))
的“findall”拆分第一组
答案 1 :(得分:0)
考虑此代码以获取单个类别ID和名称:
$str = '/products/22-test/25-test2';
if (stripos($str, "/products/") !== false &&
preg_match_all('#(/(\d+)-([a-z\d_-]+))#i', $str, $m))
print_r($m);
<强>输出:强>
Array
(
[0] => Array
(
[0] => /22-test
[1] => /25-test2
)
[1] => Array
(
[0] => 22
[1] => 25
)
[2] => Array
(
[0] => test
[1] => test2
)
)