Обернуть жирные / сильные теги вокруг первого вхождения ключевого слова во фрагмент контента? - PullRequest
1 голос
/ 30 января 2011

Я ищу самый простой способ обернуть жирные теги вокруг первого появления предопределенной ключевой фразы, когда эта фраза не появляется в теге заголовка или в качестве значения атрибута html.После того, как найдено первое совпадение, выходит из подпрограммы.

Например, если ключевым словом является «синие виджеты», а содержимое было:

blue widgets and accessories for blue widgets can be found here

Затем после подпрограммы фильтруется содержимое, он будет возвращать:

<b>blue widgets</b> and accessories for blue widgets can be found here

Однако, если первое вхождение слова «синие виджеты» было в атрибуте или теге заголовка, оно пропустило бы их и перешло к следующему.Например,

<img src="foo.png" title="A site about blue widgets" alt="blue-widget" />
<h2>This is a site about blue widgets</h2>
<p>We've got lots of blue widgets and blue widget accessories...

В приведенном выше содержании только появление ключевого слова в предложении "У нас много синих виджетов и синих аксессуаров для виджетов" ...быть смелым.

Может ли кто-нибудь дать мне пример того, как это можно сделать?

1 Ответ

1 голос
/ 31 января 2011

Если вы все еще думаете об использовании регулярных выражений, проверьте это:

$source = <<<EOS
<img src="foo.png" title="A site about blue widgets" alt="blue-widget" />
<h2>This is a site about blue widgets</h2>
<p>We've got lots of blue widgets and blue widget accessories...';
EOS;

$term = 'blue widgets';

// convert search term to valid regex
$term0 = preg_replace(array('~\A\b~', '~\b\z~', '~\s+~'), 
                      array('\b', '\b', '\s+'),
                      preg_quote(trim($term), '~'));

$regex = <<<EOR
~\A   # anchoring at string start ensures only one match can occur
(?>
   <(h[1-6])[^>]*>.*?</\\1>   # a complete h<n> element
 | </?\w+[^>]*+>              # any other tag
 | (?:(?!<|{$term0}).)*+      # anything else, but stop before '<' or the search term
)*+
\K    # pretend the match really started here; only the next part gets replaced
{$term0}
~isx
EOR;

echo preg_replace($regex, "<strong>$0</strong>", $source);

запустите его на ideone.com

Я даже не был уверен, что возможно сделать это с помощью регулярного выражения, поэтому я решил разобраться с этим. Несмотря на то, что это решение отвратительно, оно настолько простое, насколько я мог. И чтобы сделать это, мне пришлось игнорировать многие факторы, которые могут его нарушить - например, разделы CDATA, комментарии SGML, элементы <script> и угловые скобки в значениях атрибутов. И это только в допустим HTML.

Забавно, как это было, но я надеюсь, что это убедит вас раз и навсегда забыть о регулярных выражениях и использовать специальный инструмент, как советовали другие респонденты.

...