PHP preg_replace函数替换以前的匹配

时间:2012-07-06 12:10:18

标签: php preg-replace

我有一个相当基本的情况,我有一个字符串数组,我想在一个字符串中找到所有匹配项,并在它们周围添加强标记。这就是我到目前为止所做的:

$searchWords = array("test","this","s");

for($i=0;$i<sizeof($searchWords);$i++) {
    $searchWords[$i] = "/".preg_quote($searchWords[$i])."/i";
}

$label = "This is a test string.";

$result = preg_replace($searchWords, "<strong>$0</strong>", $label);

echo($result);

问题在于preg_replace函数似乎与“s”搜索项匹配,因为它们被替换为强标记。所以我最终得到了:

  

&LT;强&GT; Thisstrong&GT;是一个&lt; strong&gt; teststrong&gt;。

当我真正想要的是:

  

&LT;强&gt;这&LT; /强&GT; I&LT;强&GT; S&LT; /强&GT; &lt; strong&gt;测试&lt; / strong&gt;。

那么,你们可以建议我哪里出错吗?

非常感谢任何帮助,我正在撕裂我的头发,我必须亲近。

2 个答案:

答案 0 :(得分:3)

你不想做三个替换,而是一个:

$result = preg_replace("#" . implode($searchWords, "|") . "#", "<strong>$0</strong>", $label);

hakre的编辑:这就像这个或那个或那个字符串一样。第一场比赛将被采取。所以从最长的字符串开始,把最小的字符串作为最后一个字符串。

二进制文件对此编辑的回答:见评论


完整版:

<?php
$searchWords = array("t", "test", "this");
usort($searchWords, function ($a, $b) { return strlen($b) - strlen($a); });

foreach ($searchWords as &$word)
{
    $word = preg_quote($word);
}
unset($word);

$label = "This is a test string.";

$searchWords = implode($searchWords, "|");
$result = preg_replace("#{$searchWords}#i", "<strong>$0</strong>", $label);

echo($result);

答案 1 :(得分:0)

确保不发生这种情况的最简单方法是使用两个不会被替换的特殊“faketags”,然后替换它们,或者指定单词必须是完整的单词匹配并且开始和结束于一个词边界。

  $result = preg_replace($searchWords, "<_^_>$0</_^_>", $label);
  $result = str_replace('_^_', 'strong', $result);

  $searchWords[$i] = '/\b'.preg_quote($searchWords[$i]).'\b/i';

第二个更优雅(更快 - 也加快搜索速度,我敢打赌)但是阻止你使用部分单词替换。