-1

我正在尝试匹配一个模式i2,3 位数字,然后是一个破折号-和 1 到 3 位数字。

示例数据

i2123-1
i2121-20
i2111-331
i2111
i21111
i2111-1141

应该只匹配

i2123-1
i2121-20
i2111-331

我试过了,但它不匹配某些模式,并且对于某些模式匹配太多。

preg_match_all('/i2\d{3}-\d{3}/', $str, $matches);
4

3 回答 3

1

您需要将您的最后一个更改\d{3}\d{1,3}在破折号后接受 1 到 3 个数字。但即便如此,你仍然会比你想要的更多,我会\b为这种特定情况使用单词边界。

preg_match_all('/\bi2\d{3}-\d{1,3}\b/', $str, $matches);

观看现场演示

于 2013-10-12T16:53:06.320 回答
0

您只需要使用{m,n}格式使量词接受更少并使用单词边界:

/i2\d{3}-\d{1,3}\b/

或者,一个否定的前瞻,或者一个锚(如果你不想匹配i2123-123-):

/i2\d{3}-\d{1,3}(?!.)/

/i2\d{3}-\d{1,3}$/      

最后一个可能需要多行模式:

preg_match_all('/i2\d{3}-\d{1,3}$/m', $str, $matches);

正则表达式101演示

如果您想绝对确定该模式中没有其他内容,请使用锚点和多行模式(如果您另外在单个字符串中测试多行:

preg_match_all('/^i2\d{3}-\d{1,3}$/m', $str, $matches);
于 2013-10-12T16:53:25.400 回答
0

我相信正确的解决方案也需要包含\b在模式的开头,所以我会使用

preg_match_all('/\bi2\d{3}-\d{1,3}\b/', $str, $matches);

针对此示例输入测试此解决方案和其他已发布的解决方案:

i2123-1
i2121-20
i2111-331
i2111
i21111
i2111-1141
 i2123-1
1i2121-20
ai2111-331

请参阅此演示

于 2013-10-12T21:38:28.773 回答