PHP regexp模式中需要额外的反斜杠

PHP regexp模式中需要额外的反斜杠,php,regex,pcre,Php,Regex,Pcre,在测试答案时,我发现了一些我不理解的东西。问题是将字符串中的所有文字\t\n\r字符替换为单个空格 现在,我尝试的第一种模式是: /(?:\\[trn])+/ 令人惊讶的是,这没有起作用。我在Perl中尝试了相同的模式,效果很好。经过一些尝试和错误,我发现PHP需要3或4个反斜杠来匹配该模式,如下所示: /(?:\\\\[trn])+/ 或 令我惊讶的是,这些模式都有效。为什么需要这些额外的反斜杠?在正则表达式中需要4个反斜杠来表示1,因为: 2个反斜杠用于在字符串中取消跳过(“\\\\”

在测试答案时,我发现了一些我不理解的东西。问题是将字符串中的所有文字
\t
\n
\r
字符替换为单个空格

现在,我尝试的第一种模式是:

/(?:\\[trn])+/
令人惊讶的是,这没有起作用。我在Perl中尝试了相同的模式,效果很好。经过一些尝试和错误,我发现PHP需要3或4个反斜杠来匹配该模式,如下所示:

/(?:\\\\[trn])+/


令我惊讶的是,这些模式都有效。为什么需要这些额外的反斜杠?

在正则表达式中需要4个反斜杠来表示1,因为:

  • 2个反斜杠用于在字符串中取消跳过(
    “\\\\”->\\\
  • 1反斜杠用于在正则表达式引擎中取消跳过(
    \\->\
从PHP文档中

转义任何其他字符也会导致打印反斜杠

因此,对于
\\\[

  • 1个反斜杠用于取消跳过
    \
    ,一个停留是因为
    \[
    无效(
    “\\\[”->\\[
  • 1反斜杠用于在正则表达式引擎中取消跳过(
    \\[->\[
是的,它是有效的,但不是一个好的实践。

正则表达式只是
/(?:\\[trn])+/
。但是由于您也需要在字符串声明中转义反斜杠,因此每个反斜杠必须用
\
表示:

"/(?:\\\\[trn])+/"
'/(?:\\\\[trn])+/'

因为PHP不知道转义序列
\[
并忽略它,所以只有三个退格也可以工作。所以
\
将变成
\
,但是
\[/code>将保持
\[

它在perl中工作,因为您直接以正则表达式模式
/(?:\[trn])+//code>传递它

但在php中,需要作为字符串传递,因此需要对反斜杠本身进行额外的转义

"/(?:\\\\[trn])+/"
正则表达式\用于匹配单个 反斜杠将变为“/\/”作为

使用str_替换

$code = str_replace(array("\t","\n","\r"),'',$code);

应该这样做

那么为什么3个反斜杠有效?为什么在这种情况下单引号和双引号没有区别?Gumbo::我知道我是否理解正确--这种情况有效,因为
\[
不是一个控制字符,它也不会变成一个开方括号,因为模式是从左到右解析的,所以反斜杠会附加到它前面的一个字符上,并且以前被转义过?@kemp:是的,只有手册中列出的转义序列被替换。这不能回答我的问题,而且也是错误的,因为str_replace()不允许用一个引号替换所有请求的字符(无论它们有多少)——您可以将它们全部删除。@kemp yes确实可以。如果它不按原样删除,请尝试\r\n或\n\r\n组合,则不能替换-say-3(或任意数)除非您想提供所有可能的组合,否则您的代码只需将它们全部删除。Perl正则表达式集成到语言中,所以您只需要两个反斜杠。
$code = str_replace(array("\t","\n","\r"),'',$code);