正则表达式:如何转义反斜杠和特殊字符?

14

是否有一种方法可以在正则表达式中转义(或保护)特殊字符?

我想做的是创建一个简单的正则表达式测试器:

import java.util.regex.*;
class TestRegex { 
   public static void main( String ... args ) { 
       System.out.printf("%s ~= %s ? %s  %n" , args[0], args[1], Pattern.matches( args[0], args[1] ) );
   }
}

这在将模式插入程序之前进行测试非常有效:

$java TestRegex "\d" 1
\d ~= 1 ? true  
$java TestRegex "\d" 12
\d ~= 12 ? false  
$java TestRegex "\d+" 12
\d+ ~= 12 ? true  
$java TestRegex "\d+" a12
\d+ ~= a12 ? false  
$java TestRegex "\d+" ""
\d+ ~=  ? false  

接下来我要在我的程序中使用这个模式,但每次都需要手动转义它:

Pattern p = Pattern.compile( /*copy pasted regex here */ );

在这个示例中,请将 \d 替换为 \\d。过一段时间后,这会变得非常烦人。

问:我如何自动转义这些特殊字符?

1个回答

28

你只需要将所有单个反斜杠替换为双反斜杠。这有点复杂,因为在String上的replaceAll函数实际上执行的是正则表达式,所以你必须先转义反斜杠,因为它是一个字面量(得到\\),然后再转义一次,因为是正则表达式(得到\\\\)。替换也遭遇了类似的命运,需要两个这样的转义序列,总共需要8个反斜杠:

System.out.printf("%s ~= %s ? %s  %n", 
    args[0].replaceAll("\\\\","\\\\\\\\"), args[1], ...

我得到了以下错误信息:Exception in thread "main" java.util.regex.PatternSyntaxException: Unexpected internal error near index 1。链接为http://pastebin.com/aEWSibXv。 - OscarRyz
2
就像这样的时刻,我希望Java有更好的字面字符串语法。 - Hiro2k
@Oscar:哎呀,你必须对字符串文字进行一次转义,另一次是因为replaceAll本身就是一个正则表达式。现在已经修复了。 - Mark Elliot
我离成功还有一点距离.. 我正在尝试几种组合 :) 那么特殊字符,比如 + { ( 等等呢?我认为我不需要转义它们,对吗? - OscarRyz
@Oscar:不,唯一会导致问题的字面量是反斜杠。具有讽刺意味的是,我犯的错误与你试图解决的错误完全相同。 - Mark Elliot
这基本上证明了这一点 ;) 像魔法一样工作,谢谢:http://pastebin.com/y0mePwV5 - OscarRyz

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