【问题标题】:Php preg_replace replace all matching content between two tags, except content contained in another two specific tagsphp preg_replace 替换两个标签之间的所有匹配内容,除了另外两个特定标签中包含的内容
【发布时间】:2018-02-26 07:10:28
【问题描述】:

我有这个 html:

(text)Text one(/text)(text)text two(/text)<input type="text" name="name" 
id="name" value="(text)text three(/text)" />(text)Text four(/text)

我想替换包含在 (text) 和 (/text) 之间的单词和相对 (text) (/text) 标签,但输入/textarea 值中包含的标签除外。

我想使用正则表达式,而不是 dom

其实我在用:

preg_replace("~\\(text\)[\s\S]+?\\(\/text\)~","replacing text",$content);

但是这个替换了所有内容,也替换了输入/文本区域中的内容

谢谢

【问题讨论】:

    标签: php regex preg-replace


    【解决方案1】:

    您可以实施(*SKIP)(*FAIL) 技术来匹配&lt;input...&gt; 标记并取消其替换资格。这将允许按预期替换所有(text)...(/text) 子字符串。

    Pattern&Replacement Demo

    代码:(Demo)

    $html=<<<HTML
    (text)Text one(/text)(text)text two(/text)<input type="text" name="name" 
    id="name" value="(text)text three(/text)" />(text)Text four(/text)
    HTML;
    
    echo preg_replace('~<input[^>]+>(*SKIP)(*FAIL)|\(text\).*?\(/text\)~','[*]',$html);
    

    输出:

    [*][*]<input type="text" name="name" 
    id="name" value="(text)text three(/text)" />[*]
    

    ...现在是精美的印刷品

    • 通常不建议使用正则表达式来解析 html,因为它会一直工作,直到由于输入字符串本身的边缘情况/异常而突然/默默地无法工作。像 DomDocument 这样的 html 解析器通常是推荐的工具。
    • 我不确定您是否正在执行任何动态替换文本,或者是否所有替换都接收到相同的静态值。如果您需要执行动态替换,preg_replace_callback() 可能是完成这项工作的最佳工具。
    • 我的模式非常适合您的输入字符串。根据实际项目中数据的可变性,可能需要对模式进行细化/调整。
    • 我的模式在(text)(/text) 之间使用.*? 以允许( 字符的可能性。如果您知道在这些相对位置不会有(,您可以改用[^(]* 来提高模式效率。输入标签部分中的[^&gt;]+ 也相反——如果您的项目数据在这些标签中包含&gt;,那么您可以使用.*?,但会降低效率。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-01-06
      • 1970-01-01
      相关资源
      最近更新 更多