Java Regex:为什么\ 177转义代码无效?

时间:2016-08-03 16:44:46

标签: java regex

我正在使用常见的正则表达式验证电子邮件。模式是:

(^[-!#$%&'*+/=?^_`{}|~0-9A-Z]+(\.[-!#$%&'*+/=?^_`{}|~0-9A-Z]+)*|^"([\001-\010\013\014\016-\037!#-\[\]-\177]|\\[\001-\011\013\014\016-\177])*")@((?:[A-Z0-9](?:[A-Z0-9-]{0,61}[A-Z0-9])?\.)+[A-Z]{2,6}\.?$)|\[(25[0-5]|2[0-4]\d|[0-1]?\d?\d)(\.(25[0-5]|2[0-4]\d|[0-1]?\d?\d)){3}\]$

以防万一,我在java中添加了所有\ escaping,所以这是java评估的最终模式。它适用于普通的在线正则表达式评估程序,但在Java中运行时会抛出

  

java.util.regex.PatternSyntaxException:索引103附近的非法/不支持转义序列

这是\ 177代码。为什么这样,为什么该代码是非法的,为什么它在在线验证器中起作用?

3 个答案:

答案 0 :(得分:4)

The javadoc of Pattern在这里给出了答案;引用:

\0n     The character with octal value 0n (0 <= n <= 7)
\0nn    The character with octal value 0nn (0 <= n <= 7)
\0mnn   The character with octal value 0mnn (0 <= m <= 3, 0 <= n <= 7)

出现八进制转义序列的唯一有效方法是上面的。

如果您为\1xx编写xx,则会将其解释为\1然后xx,其中\1是对第一个...37!#-\[\]-\177]|\\ ^^ HERE 的反向引用捕获正则表达式组...

除非在您的情况下,索引103位于:

\0177

你是一个角色类;并且你不能在字符类中使用反向引用。因此,正则表达式引擎试图将其解释为转义序列,如上所述,这是非法的。因此消息。

将其替换为{{1}},您的问题就会得到解决。

作为旁注,验证带有正则表达式的电子邮件虽然很常见,但也是一个非常糟糕的主意。请改用javax.mail,它可以使用InternetAddress验证邮件地址。

[进一步说明:虽然上面的链接是Java EE,但实际上你可以将javamail作为一个独立的jar添加到你的项目中;快速的maven搜索会告诉你]

答案 1 :(得分:0)

内联正则表达式验证器往往会产生误导,因为有许多不同类型的正则表达式。您需要一个Java正则表达式,但您的验证器显然正在测试相关但不同的风格。

针对您的具体问题:从the documentation for java.util.regex.Pattern可以看出,八进制转义必须以\0开头,但之后最多可以有三位数。因此,请将\177更改为\0177

答案 2 :(得分:0)

在课堂之外,Java将八进制视为\0377,以区别于它 反向引用。

其他引擎将采用\377形式,但使用内部捕获组
在这一点上的认可,以区别于反向引用 这些其他引擎不会识别类中的\nnn形式,
但为此提供了一个八进制括号形式\o{nnn}

据我所知,您可以尝试\0377内部课程,看看是否有 这是有效的,否则我不知道Java是否在课堂上识别八进制。