PHP Regexp优化现有模式

时间:2018-03-02 15:06:47

标签: php regex preg-match preg-match-all

我正在使用此代码

preg_match_all("/([^#]+\btbds\b.+?)#/iu", $data, $matches);   

找到所有名为tbds的单词,但它需要大约1.20秒来执行模式搜索。如果我只使用tbds \ b而不是\ btbds \ b它只需0.19秒(少6倍)。

preg_match_all("/([^#]+tbds\b.+?)#/iu", $data, $matches); 

有没有办法优化单词match \ btbds \ b大约0.19秒?我需要处理大量数据。谢谢你提前。

这是测试代码:

function generateRandomString($length = 10) {
    $characters = ' 0123 456 789 abcd efgh ijkl mn opqrstu vwx yzAB CDE FGHI JKL MNOP QRS TUVWX YZ';
    $charactersLength = strlen($characters);
    $randomString = '';
    for ($i = 0; $i < $length; $i++) {
        $randomString .= $characters[rand(0, $charactersLength - 1)];
    }
    $randomString = preg_replace('/\s+/', ' ', $randomString);
    return trim($randomString,' ');
}


$data=NULL;
for ($a = 1; $a < 1000000; $a++) 
    $data.=" ".generateRandomString(100)." #";


$t = microtime(true);
preg_match_all("/([^#]+\btbds\b.+?)#/iu", $data, $matches); 
echo microtime(true) - $t; echo "\n";

2 个答案:

答案 0 :(得分:1)

前缀[^#]+

使你的正则表达式变慢的原因

如果你定义一个起点可以是#开始字符串,也许会有所帮助:

/(?:(?<=#)|^)([^#]*\btbds\b.+?)#/iu

The Demo

答案 1 :(得分:1)

也许这可以与#匹配,然后使用\K重置报告的匹配的起点。

然后与[^#]+匹配#一次或多次,然后在字边界tbds之间匹配\btbds\b

#\K[^#]+\btbds\b[^#]+#