如何使用preg_replace_callback?

时间:2012-06-24 03:46:48

标签: php preg-replace preg-replace-callback

我有以下HTML声明

[otsection]Wallpapers[/otsection]
WALLPAPERS GO HERE

[otsection]Videos[/otsection]
VIDEOS GO HERE

我想要做的是用html div替换[otsection]标签。问题是我希望将div的id从1-> 2-> 3等增加。

例如,上述陈述应翻译为

<div class="otsection" id="1">Wallpapers</div>
WALLPAPERS GO HERE

<div class="otsection" id="2">Videos</div>
VIDEOS GO HERE

据我所知,最好的方法是通过preg_replace_callback来增加每个替换之间的id变量。但经过1小时的工作后,我无法让它发挥作用。

对此有任何帮助将非常感谢!

2 个答案:

答案 0 :(得分:46)

使用以下内容:

$out = preg_replace_callback(
    "(\[otsection\](.*?)\[/otsection\])is",
    function($m) {
        static $id = 0;
        $id++;
        return "<div class=\"otsection\" id=\"ots".$id."\">".$m[1]."</div>";
    },
    $in);

请注意,我使用了static变量。这个变量在函数调用过程中持续存在,这意味着每次调用函数时它都会递增,这对于每个匹配都会发生。

另请注意,我已将ots添加到ID中。元素ID不应以数字开头。


对于5.3之前的PHP:

$out = preg_replace_callback(
    "(\[otsection\](.*?)\[/otsection\])is",
    create_function('$m','
        static $id = 0;
        $id++;
        return "<div class=\"otsection\" id=\"ots".$id."\">".$m[1]."</div>";
    '),
    $in);

答案 1 :(得分:26)

  

注意:以下内容旨在作为一般性答案,并不会尝试解决OP的特定问题,因为它已经是addressed before

什么是preg_replace_callback()

此函数用于执行正则表达式搜索和替换。它类似于str_replace(),但它不是普通字符串,而是搜索用户定义的正则表达式模式,然后对匹配的项应用回调函数。如果找到匹配,则函数返回修改后的字符串,否则返回未修改的字符串。

我什么时候应该使用它?

preg_replace_callback()preg_replace()非常相似 - 唯一的区别是,不是为第二个参数指定替换字符串,而是指定callback函数。

如果要进行简单的正则表达式搜索和替换,请使用preg_replace()。如果您想做的不仅仅是替换,请使用preg_replace_callback()。请参阅下面的示例,了解其工作原理。

如何使用?

这是一个说明函数用法的例子。在这里,我们尝试将日期字符串从YYYY-MM-DD格式转换为DD-MM-YYYY

// our date string
$string  = '2014-02-22';

// search pattern
$pattern = '~(\d{4})-(\d{2})-(\d{2})~';

// the function call
$result = preg_replace_callback($pattern, 'callback', $string);

// the callback function
function callback ($matches) {
    print_r($matches);
    return $matches[3].'-'.$matches[2].'-'.$matches[1];
}

echo $result;

此处,我们的正则表达式模式搜索格式NNNN-NN-NN的日期字符串,其中N可以是0 - 9\d之间的数字}是字符类[0-9])的简写表示。将调用回调函数并传递给定字符串中匹配元素的数组。

最终结果将是:

22-02-2014

注意:以上示例仅供参考。您不应该用于解析日期。请改用DateTime::createFromFormat()DateTime::format()This question有更多详情。