Java正则表达式中的“(.*)”、“(.*)+”、“.+)*”有一个奇怪的问题
为了重新产生最近一个问题-Why does (.*)* make two matches and select nothing in group $1?中所述的问题,我尝试了*
和+
在括号内和括号外的各种组合,结果出乎意料
我本希望得到的结果与该问题中已接受的答案中所解释的结果相同,并且在另一个重复的问题中也是如此,标记在Perl
-Why doesn't the .* consume the entire string in this Perl regex?下。但它的行为方式不同
为了简单起见,以下是我尝试的代码:-
String str = "input";
String[] patterns = { "(.*)*", "(.*)+", "(.+)*", "(.+)+" };
for (String pattern: patterns) {
Matcher matcher = Pattern.compile(pattern).matcher(str);
while (matcher.find()) {
System.out.print("'" + matcher.group(1) + "' : '" + matcher.start() + "'" + "\t");
}
System.out.println();
}
这是我得到的所有4个组合的输出:-
'' : '0' '' : '5' // For `(.*)*`
'' : '0' '' : '5' // For `(.*)+`
'input' : '0' 'null' : '5' // For `(.+)*`
'input' : '0' // For `(.+)+`
现在,我不明白的是,为什么在1st
和2nd
输出中,我没有得到matcher.find()
的整个字符串作为first result
。我的意思是,理想情况下,在第一种情况下,.*
应该首先捕获整个字符串,然后在最后捕获empty string
。现在,虽然它给出了第二场比赛的预期结果,但它在1st match
中的表现并不好
而且,在第二种情况下,我甚至不应该得到第二个匹配,因为我在括号外有一个+
量词
我的预期产出是:-
'input' : '0' '' : '5' // For 1st
'input' : '0' // For 2nd
另外,在3rd
输出中,为什么我将null
作为第二个匹配而不是empty string
呢?前三个组合的第二个匹配不应该相同吗
第四个输出符合预期。所以,毫无疑问
# 1 楼答案
你看到了与你所链接的问题相同的现象的影响:
对于
(.*)*
:matcher.start()
是0
,因为这是匹配("input"
)的开始李>matcher.group(1)
是""
,因为重复的(.*)
已经用空字符串覆盖了捕获的"input"
(但是matcher.group(0)
确实包含input"
)李>matcher.start()
是5
,因为在第一次成功匹配之后,正则表达式引擎就在那里李>matcher.group(1)
(以及matcher.group(0)
)是""
,因为这是字符串末尾要匹配的全部内容李>对于
(.*)+
来说也是一样的。毕竟,空字符串可以重复任意多次,但仍然是空字符串对于
(.+)*
您会得到null
,因为当第二次匹配成功时(长度为1的字符串的零次重复匹配空字符串),捕获括号无法捕获任何内容,因此其内容是null
(如未定义,而不是空字符串)