输入
example("This is tes't")
example('This is the tes\"t')
输出
This is tes't
This is the tes"t
代码
String text = "example(\"This is tes't\")";
//String text = "$.i18nMessage('This is the tes\"t\')";
final String quoteRegex = "example.*?(\".*?\")?('.*?')?";
Matcher matcher0 = Pattern.compile(quoteRegex).matcher(text);
while (matcher0.find()) {
System.out.println(matcher0.group(1));
System.out.println(matcher0.group(2));
}
我看到输出为
null
null
虽然当我使用正则表达式example.*?(\".*?\")
时,它会返回This is tes't
,当我使用example.*?('.*?')
时,它会返回
This is the tes"t
但是当我将它们与example.*?(\".*?\")?('.*?')?
结合使用时,它返回null。为什么?
答案 0 :(得分:2)
正则表达式末尾的.*?(\".*?\")?('.*?')?
子模式序列可以匹配空字符串(所有3个部分都使用匹配0个或更多字符的*
/ *?
进行量化)。在匹配example
之后,首先跳过.*?
,并且仅在后续子模式不匹配时展开。但是,它们都匹配(
之前的空字符串,因此,example
中只有matcher0.group(0)
。
使用使第1组成为强制性的替换(demo):
Pattern.compile("example.*?(\".*?\"|'.*?')"
或者带有驯化贪婪令牌(demo)的变体,可以摆脱交替:
Pattern.compile("example.*?(([\"'])(?:(?!\\2).)*\\2)"
或者,更好的是,支持转义序列(another demo):
Pattern.compile("example.*?(\"[^\"\\\\]*(?:\\\\.[^\"\\\\]*)*\"|'[^'\\\\]*(?:\\\\.[^'\\\\]*)*')"
在所有3个示例中,您只需要访问第1组。如果(
与example
或"
之间只能'
,则应替换{{ 1}} .*?
,因为它会使匹配更安全。虽然,使用正则表达式匹配字符串文字(至少使用一个正则表达式)永远不会太安全。