如何将单个 替换为一个空格,但如果有多个 则不替换?

5
我认为正则表达式可能是解决问题的办法,但我一直没有能够想出一个可行的解决方案。在PHP中,我有一些相当长的字符串需要清理。在某些情况下, 代替了单个空格字符,在其他情况下出现了   (等等)。我想用空格替换所有单个 出现的位置,但保留其他位置,以便保持意图不变。
有什么想法吗?我认为这里可以使用正则表达式,但我已经苦于无法制定一个有效的方案!

你想用什么来替换一个空格和一个 ? - Casimir et Hippolyte
Swishhhhh-HoHe-Swishhhhh-有人在这里吗?你是在你的代码编辑器里做这个吗?如果是的话,你用的是什么编辑器? - Casimir et Hippolyte
1
另一种想法是使用 preg_replace_callback('#( )+#'),回调函数检查是否匹配了一个   或多个,并相应地返回替换字符串。 - DCoder
2个回答

12
你必须使用负回顾和负预测来确保你周围没有其他的  。
$str = preg_replace('~(?<!&nbsp;)&nbsp;(?!&nbsp;)~i', ' ', $str);

有关环视的更多信息在此.


负向先行断言效果很好,我只需要在导入文本时运行一次,所以对性能并不是特别担心。 - Programming123

1
使用一个明确的正则表达式来匹配(not-&nbsp;)&nbsp;(not-&nbsp;),并将替换添加为$1 $2(匹配1个空格,匹配2)。你可能需要显式地编写not-&nbsp;,如([^;]|[^p];|[^s]p;|[^b]sp;|[^n]bsp;|[^&]nbsp;)
编辑:虽然[负面]环视可能很有用(而且肯定比总代码少),但您可能需要测量每种方法的速度。我发现正则表达式中的某些机制与其他机制相比非常缓慢,尽管我无法直接谈论环视的速度。如果速度成为问题,您可以跳过正则表达式,使用strpossubstring操作和测试的组合,这些操作和测试通常比正则表达式快得多,即使它们更加繁琐。我建议这样做只是因为您正在寻找一个非常明确的字符串;对于不太确定的字符串,正则表达式绝对是正确的选择。
对于这个示例(伪代码),您的字符串strpos搜索将简单地为strpos($mystring, "&nbsp;"),一旦找到匹配项,请调用strpos($mystring, "&nbsp;&nbsp;")。如果两个index调用返回相同的值,则可以跳过此替换并在索引点之后搜索字符串(在indexDoubleFound + 12之后开始单个&nbsp;搜索,但在indexDoubleFound + 6之后开始双重&nbsp;搜索,以确保您不会错过任何内容并且不会意外替换)。

我更新了我的答案,使用了 PHP 中正确的函数名称(strpos 而不是 index)。 - abiessu

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接