【问题标题】:What's the quickest way to strip a string from a specific tag从特定标签中删除字符串的最快方法是什么
【发布时间】:2016-08-11 12:22:35
【问题描述】:

我在一个字符串中有 HTML。我想去掉其中的<head> 部分。我用:

$html = preg_replace("/<head[^>]*?>.*?<\/head>/s", "", $html);

但就性能而言,这可能有点重。有更好的选择吗?

我知道我可以使用strip_tags() 并在第二个参数中列出所有接受的标签,但是列出的太多了。

【问题讨论】:

  • 您可以使用strpos() 来确定打开和关闭&lt;head&gt; 标签的位置,然后获取子字符串,但我不确定这是否是更好的执行方式。
  • 你可以写一个更好的正则表达式:) 就像&lt;head[^&gt;]*?&gt;[^&lt;]*(?:&lt;(?!\/head&gt;)[^&lt;]*)*&lt;\/head&gt;。与yours比较。
  • @WiktorStribiżew 就是这个!你能写出答案并解释它如何减少步骤等。非常令人印象深刻。我可以在同一个正则表达式中添加更多标签吗?就像&lt;head&gt;&lt;header&gt;&lt;nav&gt; 一样,我一口气将它们全部删除,而不是执行 3 次单独的 reg_replace() 运行。
  • @ᴳᵁᴵᴰᴼ:不幸的是,sax 在 PHP 中非常慢,只能与 XML 一起使用(与 XMLReader 相同,(来自 libxml 的拉式解析器,速度要快得多))。但由于 OP 似乎需要在他的 html 源上执行几项任务,使用 DOMDocument 不是问题,树构建的成本将被摊销。

标签: php regex


【解决方案1】:

当针对此 SO 页面的一部分进行测试时,您当前的正则表达式需要 6720 步。

这个正则表达式 &lt;head[^&gt;]*?&gt;(?:[^&lt;]*&lt;??)*&lt;/head&gt; 只需要 376 步,它应该返回同样的东西。它应该比您的正则表达式快近 20 倍。

它通过贪婪匹配所有不是&lt;的东西来工作:[^&lt;]*

然后,因为&lt;?? 是惰性的,它会尝试立即匹配&lt;/head&gt;。如果没有匹配到,&lt;?? 就会启动。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2014-03-29
    • 2017-05-19
    • 2010-09-06
    • 1970-01-01
    • 2023-01-11
    • 2022-01-04
    • 2011-05-31
    • 2012-02-01
    相关资源
    最近更新 更多