Java正则表达式-重叠匹配
在以下代码中:Java正则表达式-重叠匹配,java,regex,Java,Regex,在以下代码中: public static void main(String[] args) { List<String> allMatches = new ArrayList<String>(); Matcher m = Pattern.compile("\\d+\\D+\\d+").matcher("2abc3abc4abc5"); while (m.find()) { allMatches.add(m.group());
public static void main(String[] args) {
List<String> allMatches = new ArrayList<String>();
Matcher m = Pattern.compile("\\d+\\D+\\d+").matcher("2abc3abc4abc5");
while (m.find()) {
allMatches.add(m.group());
}
String[] res = allMatches.toArray(new String[0]);
System.out.println(Arrays.toString(res));
}
我希望是这样
如何实现这一目标 不确定这在Java中是否可行,但在PCRE中可以执行以下操作:
(?=(\d+\d+\d+)。
解释该技术是在前瞻中使用匹配的组,然后“吃”一个字符向前移动
:开始正向前瞻(?=
:开始匹配组1(
:将数字匹配一次或多次\d+
:将非数字字符匹配一次或多次\D+
:将数字匹配一次或多次\d+
:第1组结束)
:前瞻结束)
:匹配任何内容,这是“向前移动”
多亏了它,它在Java中似乎真的能工作。您只需添加反斜杠并显示第一个捕获组:
(?=(\\d+\\d+\\d+)。
。
测试日期:
使匹配器尝试从后者开始下一次扫描
\d+
Matcher m = Pattern.compile("\\d+\\D+(\\d+)").matcher("2abc3abc4abc5");
if (m.find()) {
do {
allMatches.add(m.group());
} while (m.find(m.start(1)));
}
HamZa的上述解决方案在Java中运行良好。如果您想在文本中找到特定的模式,则只需执行以下操作:
String regex = "\d+\D+\d+";
String updatedRegex = "(?=(" + regex + ")).";
如果
regex
是您正在寻找的模式,并且要重叠,您需要在其周围环绕(?=(“在开始和”)。
您需要从每个索引开始搜索;使用find(int startingIndex)方法并从每个字符位置开始搜索。当然,那么你可能会找到太多的匹配项。。。假设您希望从每个数字开始,您可以尝试对所有匹配索引的Matcher.find(String.indexOf(digits,index))进行组合迭代。我假设它是个位数,您可以从匹配开始位置备份,然后从那里查找下一个匹配。对于输入“12abc13abc14abc15”
,是否希望[12abc13、2abc13、13abc14、3abc14、14abc15、4abc15]
或[12abc13、13abc14、14abc15]
?@johnchen902:后者。解决方案解决了这个问题。@anubhava它为PCRE提供了正确的结果。这就是我所说的。是的,我只是说在Java中它没有提供预期的结果。@anubhava:我已经测试了它,它工作得很好,假设你添加了反斜杠,并显示了第一个捕获组。downvoter:downvote已经完成了这里没有意义。没有真正起作用。使用12abc13abc14abc15
作为输入,结果是[12abc13,2abc13,13abc14,3abc14,14abc15,4abc15]
而不是[12abc13,13abc14,14abc15]
。请查看问题下我和OP的评论。@johnchen902:对,您必须用替换模式(=((?如果您不希望重叠结果出现在重叠结果中:)对于前两个投票人:普通版本包含一个错误,如果没有匹配项,将抛出一个IllegalStateException
。
Matcher m = Pattern.compile("\\d+\\D+(\\d+)").matcher("2abc3abc4abc5");
if (m.find()) {
do {
allMatches.add(m.group());
} while (m.find(m.start(1)));
}
String regex = "\d+\D+\d+";
String updatedRegex = "(?=(" + regex + ")).";