【问题标题】:Auto <p> regex - fix needed自动 <p> 正则表达式 - 需要修复
【发布时间】:2012-07-16 12:59:41
【问题描述】:

我有这个功能(我在 Stackoverflow 的某处找到)自动在输出字符串中添加&lt;p&gt; 标签。

function autop ($string) {

    // Define block tags
    $block_tag_list = array ('address', 'applet', 'article', 'aside', 'audio', 'blockquote', 'button', 'canvas', 'center', 'command', 'data', 'datalist', 'dd', 'del', 'details', 'dir', 'div', 'dl', 'dt', 'embed', 'fieldset', 'figcaption', 'figure', 'footer', 'form', 'frameset', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'header', 'hgroup', 'hr', 'iframe', 'ins', 'isindex', 'li', 'map', 'menu', 'nav', 'noframes', 'noscript', 'object', 'ol', 'output', 'p', 'pre', 'progress', 'section', 'script', 'summary', 'table', 'tbody', 'td', 'tfoot', 'th', 'thead', 'time', 'tr', 'track', 'ul', 'video');

    $tags = '<' . implode ('[^>]*>|<', $block_tag_list) . '[^>]*>';

$pattern = <<<PATTERN
/
(\A|\\n\\n)(?!$tags) # Start of string or two linebreaks or anything but a block tag
(.+?) # Just about anything
(\Z|\\n\\n) # End of string or two line breaks
/isex
PATTERN;

    $string = str_replace ("\r\n", "\n", $string);
    $string = str_replace ("\r\t", "", $string);
    $string = str_replace ("\n\t", "", $string);
    $string = str_replace ("\t", "", $string);
    $string = preg_replace ($pattern, "'\\1<p>' . nl2br ('\\2') . '</p>\\3'", $string);
    $string = preg_replace ($pattern, "'\\1<p>' . nl2br ('\\2') . '</p>\\3'", $string);
    $string = str_replace ('\"', "&quot;", $string);

    return $string;
}

有这种类型的字符串:

<h1>Title</h1>

This will be wrapped in a p tag

This should be wrapped in a p tag too

输出

<h1>Title</h1>

<p>This will be wrapped in a p tag</p>

<p>This should be wrapped in a p tag too</p>

它工作正常,但有一个问题:它将紧跟在&lt;p&gt; 标记之后的HTML 标记包装在其他&lt;p&gt; 标记中,从而搞砸了代码。如果 HTML 标记位于 &lt;h1&gt; 或任何其他块标记之后,则不会发生这种情况。

将双 preg_replace 设置为单个可以解决问题,但是如果像之前的示例那样有两个段落,它只会包装第一个而不是第二个。

我觉得这只是一个很小的变化,可以让它“滴答作响”,但我想不通。

也许如果有人有一个天才的罢工...... :)

【问题讨论】:

标签: php html regex


【解决方案1】:

我不确定你是否会一直对你的解决方案感到满意,但你应该得到你想要做的事情(观看第 5 行中添加的 ?=):

$pattern = <<<PATTERN
/
(\A|\\n\\n)(?!$tags) # Start of string or two linebreaks or anything but a block tag
(.+?) # Just about anything
(?=\Z|\\n\\n) # End of string or two line breaks
/isex
PATTERN;

如果没有这个,之前的边界 \Z 将消耗下一个 \A,因此这将不再匹配。当然,删除双 preg_replace

希望这会有所帮助。

【讨论】:

  • 我知道这不是一个优雅的解决方案,但后端是由第三方提供的,所以对于这个项目,我坚持使用它。但是......该死的东西现在可以工作了,多亏了你!天才! :D
  • 没问题。我完全支持你。
猜你喜欢
  • 2014-10-17
  • 1970-01-01
  • 1970-01-01
  • 2014-02-16
  • 1970-01-01
  • 2016-01-17
  • 2013-06-27
  • 2020-01-23
相关资源
最近更新 更多