Aquí hay una solución segura UTF-8, que no solo funciona con documentos formateados correctamente, sino también con fragmentos de documentos.
El mb_convert_encoding es necesario, porque loadHtml() parece tener un error con la codificación UTF-8 (ver here y here).
El mb_substr está recortando la etiqueta del cuerpo de la salida, de esta manera recupera el contenido original sin ningún marcado adicional.
<?php
$html = '<p>Match this text and replace it</p>
<p>Don\'t <a href="/">match this text</a></p>
<p>We still need to match this text and replace itŐŰ</p>
<p>This is <a href="#">a link <span>with <strong>don\'t match this text</strong> content</span></a></p>';
$dom = new DOMDocument();
// loadXml needs properly formatted documents, so it's better to use loadHtml, but it needs a hack to properly handle UTF-8 encoding
$dom->loadHtml(mb_convert_encoding($html, 'HTML-ENTITIES', "UTF-8"));
$xpath = new DOMXPath($dom);
foreach($xpath->query('//text()[not(ancestor::a)]') as $node)
{
$replaced = str_ireplace('match this text', 'MATCH', $node->wholeText);
$newNode = $dom->createDocumentFragment();
$newNode->appendXML($replaced);
$node->parentNode->replaceChild($newNode, $node);
}
// get only the body tag with its contents, then trim the body tag itself to get only the original content
echo mb_substr($dom->saveXML($xpath->query('//body')->item(0)), 6, -7, "UTF-8");
Referencias:
1. find and replace keywords by hyperlinks in an html fragment, via php dom
2. Regex/DOMDocument - match and replace text not in a link
3. php problem with russian language
4. Why Does DOM Change Encoding?
leí docenas de respuestas en el tema, así que lo siento si he olvidado a alguien (por favor comente y lo haré agregue el suyo también en este caso).
Gracias por Gordon y todavía para comentar sobre my other answer.
Utilice DOM [como se muestra] (http://stackoverflow.com/questions/4003031/how-to-replace-text-urls-and-exclude-urls-in-html-tags/4037753#4037753) aquí y adaptar – Gordon
¿Cuál es su comportamiento preferido con etiquetas anidadas dentro del ancla, como '
Esto es a link with don't match this text content
'? –