我刚刚发现了这样的Java代码:
"bla;bla;bla".split("\\;");
它返回:
["bla","bla","bla"] // String array of course
String.split确实使用正则表达式,但是根据我的研究,我发现;
不是正则表达式中的特殊字符,并且不必转义。所以我尝试将其替换为:
"bla;bla;bla;".split(";");
它仍然是一样的!那么这里发生了什么? Java试图变得更好并忽略正则表达式中无用的反斜杠吗?但我也用Notepad ++尝试过它,并且它也都找到了一个semikolon。
答案 0 :(得分:3)
在以下代码中:
"bla;bla;bla".split("\\;");
String#split()
在正则表达式上下文中执行。两个反斜杠\\
会产生文字反斜杠,因此您最终会在\;
上进行拆分,这在功能上与在;
上拆分相同,因为分号不需要转义。
如果您尝试了以下拆分,则不会得到您期望的结果:
"bla;bla;bla".split("\\\\;");
在正则表达式中,这将与文字\;
分开。由于该分隔符永远不会出现在您的字符串中,您只需获得一个数组,其第一个元素是该输入字符串。
请参阅@AndyTurner的答案,了解为何首先允许拆分\;
。
答案 1 :(得分:2)
来自the Javadoc of Pattern
(强调我的):
反斜杠字符('\')用于引入转义构造
...
在任何不表示转义构造的字母字符之前使用反斜杠是错误的;这些保留用于将来对正则表达式语言的扩展。 可以在非字母字符之前使用反斜杠,无论该字符是否为非转义构造的一部分。
答案 2 :(得分:0)
答案很好。但是,没有人提到Pattern.quote()
Java没有原始字符串或文字字符串(例如C#中的@"...";
逐字字符串或Python中的r"..."
原始字符串)。尽管如此,对于正则表达式,我们使用quote
方法返回指定String的文字模式String:
此方法生成一个可用于创建Pattern的String 这将匹配字符串s,就好像它是一个文字模式。
因此,如果您使用quote
指定模式,则不会发生拆分,如以下代码示例所示:
import java.util.regex.Pattern;
class Example
{
public static void main (String[] args) throws java.lang.Exception
{
String sourcestring = "bla;bla;bla";
Pattern re = Pattern.compile(Pattern.quote("\\;"));
String[] parts = re.split(sourcestring);
for(int partsIdx = 0; partsIdx < parts.length; partsIdx++ ){
System.out.println( "[" + partsIdx + "] = " + parts[partsIdx]);
}
}
}
输出:
[0] = bla;bla;bla
否则,它只是在Tim和Andy所解释的split
方法的正则表达式上下文中的一个转义分号。