【问题标题】:Detect HTML tags in a string检测字符串中的 HTML 标签
【发布时间】:2011-04-20 15:22:18
【问题描述】:

我需要检测一个字符串是否包含 HTML 标签。

if(!preg_match('(?<=<)\w+(?=[^<]*?>)', $string)){ 
    return $string;
}

上面的正则表达式给了我一个错误:

preg_match() [function.preg-match]: Unknown modifier '\'

我对正则表达式不太了解,所以不确定问题出在哪里。我试图逃避 \ 并没有做任何事情。

有没有比正则表达式更好的解决方案?如果不是,那么与 preg_match 一起使用的正确正则表达式是什么?

【问题讨论】:

  • / 添加到正则表达式字符串的开头和结尾

标签: php


【解决方案1】:

一个简单的解决方案是:

if($string != strip_tags($string)) {
    // contains HTML
}

与正则表达式相比,这样做的好处是更容易理解,但我无法评论这两种解决方案的执行速度。

【讨论】:

  • +1 这是检测标签是否存在的最简单方法。你甚至不需要strlen
  • 不错的答案!简单得多,尽管我认为通常正则表达式非常快。
  • 这也会告诉 一个 html 标签。
  • 如果字符串包含任何控制字符,如 /n /r...,上述代码将返回误报
  • @R1CHY_RICH:你能提供一个你描述的误报的例子吗?以下为我发出“无 html”:$s = "hello\r\nworld"; if (strip_tags($s) != $s) { echo 'contains html'; } else { echo 'no html'; }
【解决方案2】:

您需要用某个字符或其他字符“分隔”正则表达式。试试这个:

if(!preg_match('#(?<=<)\w+(?=[^<]*?>)#', $string)){ 
    return $string;
}

【讨论】:

  • 用这句话测试:'一个樱桃的重量覆盆子。
  • (?) 更适合我
【解决方案3】:

如果您只是想检测/替换某些标签:此函数将搜索某些 html 标签并将它们封装在括号中 - 这非常没有意义 - 只需将其修改为您想要对标签执行的任何操作。

$html = preg_replace_callback(
    '|\</?([a-zA-Z]+[1-6]?)(\s[^>]*)?(\s?/)?\>|',
    function ($found) {
        if(isset($found[1]) && in_array(
            $found[1], 
            array('div','p','span','b','a','strong','center','br','h1','h2','h3','h4','h5','h6','hr'))
        ) {
            return '[' . $found[0] . ']';
        };
    },
    $html  
);

正则表达式的解释:

\< ... \>   //start and ends with tag brackets
\</?        //can start with a slash for closing tags
([a-zA-Z]+[1-6]?)    //the tag itself (for example "h1")
(\s[^>]*)? //anything such as class=... style=... etc.
(\s?/)?     //allow self-closing tags such as <br />

【讨论】:

    【解决方案4】:

    如果目的只是检查字符串是否包含 html 标签。无论 html 标签是否有效。那你可以试试这个。

    function is_html($string) {
      // Check if string contains any html tags.
      return preg_match('/<\s?[^\>]*\/?\s?>/i', $string);
    }
    

    这适用于所有有效或无效的 html 标签。你可以在这里查看确认https://regex101.com/r/2g7Fx4/3

    【讨论】:

    • 为什么要区分大小写的模式修饰符?为什么&gt;在否定字符类中被转义了?
    【解决方案5】:

    我会使用 strlen(),因为如果您不这样做,则会进行逐个字符的比较,这可能会很慢,但我希望一旦发现差异,比较就会退出。

    【讨论】:

      【解决方案6】:

      我建议您只允许定义的标签!您不希望用户键入&lt;script&gt; 标记,这可能会导致 XSS 漏洞。

      试试看:

      $string = '<strong>hello</strong>';
      $pattern = "/<(p|span|b|strong|i|u) ?.*>(.*)<\/(p|span|b|strong|i|u)>/"; // Allowed tags are: <p>, <span>, <b>, <strong>, <i> and <u>
      preg_match($pattern, $string, $matches);
      
      if (!empty($matches)) {
          echo 'Good, you have used a HTML tag.';
      }
      else {
          echo 'You didn\'t use a HTML tag or it is not allowed.';
      }
      

      【讨论】:

      • 您不应该使用反向引用\1 来确保标签平衡吗?
      【解决方案7】:

      解析 HTML 通常是一个难题,这里有一些很好的材料:

      但是关于您的问题(“更好的”解决方案) - 可以更具体地说明您想要实现的目标,以及您可以使用哪些工具?

      【讨论】:

        【解决方案8】:

        如果你不擅长正则表达式(比如我),我会发现很多正则表达式库可以帮助我完成任务。

        这是一个小教程,将explain what your trying to do in php.

        我指的是one of those libraries

        【讨论】:

          猜你喜欢
          • 2017-05-28
          • 1970-01-01
          • 2011-03-11
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2021-03-03
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多