Heim > Fragen und Antworten > Hauptteil
Für eine bestimmte Zeichenfolge (normalerweise einen Absatz) möchte ich einige Wörter/Phrasen ersetzen, sie aber ignorieren, wenn sie zufällig auf irgendeine Weise von Tags umgeben sind. Dabei muss auch die Groß-/Kleinschreibung beachtet werden.
Nehmen Sie dies als Beispiel:
You can find a link here <a href="#">link</a> and a lot of things in different styles. Public platform can appear in bold: <b>public platform</b>, and we also have italics here too: <i>italics</i>. While I like soft pillows I am picky about soft <i>pillows</i>. While I want to find fox, I din't want foxes to show up. The text "shiny fruits" is in a span tag: one of the <span>shiny fruits</span>.
Angenommen, ich möchte diese Wörter ersetzen:
link
:出现 2 次。第一个是纯文本(匹配),第二个是 A
markieren (ignorieren)公共平台
:纯文本(匹配,不区分大小写),B
Zweiter im Tag (ignoriert) softpillows
: 1 Nur-Text-Übereinstimmung. fox
: 1 Nur-Text-Übereinstimmung. Es werden vollständige Wörter angezeigt. fruits
:纯文本(匹配),span
Zweiter im Tag (ignoriert) mit anderem Text Als Hintergrund suche ich nach Phrasenübereinstimmungen (nicht nach einzelnen Wörtern) und verlinke die Übereinstimmungen mit verwandten Seiten.
Ich möchte verschachteltes HTML (fett keine Linksinnerhalb eines the <a href="#">phrase <b>goes</ a> 这里</b>
Tags und umgekehrt) oder andere Fehler (z. B.:
vermeiden
Ich habe ein paar Dinge ausprobiert, wie zum Beispiel die Suche nach einer bereinigten Kopie des Textes, bei dem der HTML-Inhalt entfernt wurde, und obwohl dies mir sagte, dass es eine Übereinstimmung gab, stieß ich auf ein ganz neues Problem bei der Zuordnung zum ursprünglichen Inhalt. 🎜P粉5949413012024-03-28 12:56:47
我发现了关于正则表达式否定前瞻的提及,并且在打破我的想法之后得到这个正则表达式(假设你有VALID html标签配对)
// made function a bit ugly just to try to show how it comes together
public function replaceTextOutsideTags($sourceText = null, $toReplace = 'inner text', $dummyText = '(REPLACED TEXT HERE)')
{
$string = $sourceText ?? "Inner text
You can find a link here link and a lot
of things in different styles. Public platform can appear in bold:
public platform, and we also have italics here too: italics.
While I like soft pillows I am picky about soft pillows.
While I want to find fox, I din't want foxes to show up.
The text \"shiny fruits\" is in a span tag: one of the shiny fruits.
The inner text like this inner inner text here to test too, event inner text
omg thats sad... or not
";
// it would be nice to use [[:punct:]] but somehow regex thinks that < and > are also punctuation marks
$punctuation = "\.,!\?:;\\|\/=\"#"; // this part might take additional attention but you get the point
$stringPart = "\b$toReplace\b";
$excludeSequence = "(?![\w\n\s>$punctuation]*?";
$excludeOutside = "$excludeSequence<\/)"; // note on closing )
$excludeTag = "$excludeSequence>)"; // note on closing )
$pattern = "/" . $stringPart . $excludeOutside . $excludeTag . "/im";
return preg_replace($pattern, $dummyText, $string);
}
带有默认参数的示例输出
""" (REPLACED TEXT HERE)\r\n You can find a link here link and a lot \r\n of things in different styles. Public platform can appear in bold: \r\n public platform, and we also have italics here too: italics. \r\n While I like soft pillows I am picky about soft pillows. \r\n While I want to find fox, I din't want foxes to show up.\r\n The text "shiny fruits" is in a span tag: one of the shiny fruits.\r\n The (REPLACED TEXT HERE) like this inner inner text here to test too, event (REPLACED TEXT HERE)\r\n omg thats sad... or not """
现在一步一步
pillowS
,我们就不需要 pillow
)\w
单词符号、\s
空格或 \n
换行符和 允许以开始结束标记
结尾的标点符号 - 我们不需要这个匹配,这里出现了否定的先行 (?![\w\n\s>$标点符号]*?<\/)
。在这里我们可以确定匹配不会进入新标签,因为 <
不在描述的序列中($excludeOutside
变量)$excludeTag
变量与 $excludeOutside
基本相同,但适用于 $toReplace
可以是 html 标签本身的情况,例如 一个
<
或 >
覆盖文本,并且使用这些符号可能会导致意外行为