PHP Regex去除多余的标点符号


PHP Regex to strip excess punctuation

因此,基本上我们需要一个正则表达式来从字符串中去除多余的标点符号,只留下一个标点符号。

因此:

这是我的棒极了!!!!!你不喜欢它吗???!!??!!

将导致

这是我棒极了的绳子!你不喜欢吗?!

我试了又试,但我要么把绳子弄碎,要么根本不管用。我还在学习Regexes,所以请原谅这个愚蠢的问题。

我想"标点符号"几乎是任何不是A-Za-z0-9 的东西

编辑看来我误解了我们最初的要求。使用下面公认的解决方案,我该如何调整它,以便无论你有什么字符,标点符号都只限于第一个?

IE

会变成

这是我的绳子!!!?!?!?!?是不是很棒???!?!?!!

将成为

这是我的绳子!这不是很棒吗?

与其他答案类似,但应按任何顺序处理任何非0-9a-zA-Z字符,每个字符只剩下一个:

$newstring= preg_replace('/([^'w's])(?=[^'w's]*'1)/', '', $oldstring);

应转动

This is my awesome string!!!!! Don't you love it???!!??!!

进入

This is my awesome string! Don't you love it?!

它的工作原理是使用正向前瞻来查看该字符是否再次出现在该标点符号字符串中。如果是,它将被替换为空字符串。

尝试preg_replace_callback:

preg_replace_callback('/[!?]+/', function($m) {
    $excl = strpos($m[0], '!');
    $ques = strpos($m[0], '?');
    if($excl !== false && $excl <= $ques) {
        return $ques === false ? '!' : '!?';
    } else {
        return $excl === false ? '?' : '?!';
    }
}, $str);

这是一个演示。

也许是preg_replace('#([!?])'1+#', '$1')之类的东西?例如:

$t = 'This is my awesome string!!!!! Don''t you love it???!!??!!';
$u = preg_replace('#([!?])'1+#', '$1', $t);
// to clear out all these '?!?!...' and '!?!?...' sequences.
$u = preg_replace('#('?!|!'?)'1+#', '$1', $u); 

echo $u; // This is my awesome string! Don't you love it?!