如何仅在某些行上获得多个Java正则表达式匹配

Mat*_*one 4 java regex multiple-matches regex-group regex-lookarounds

我正在调用一个我无法更改的API.也就是说,我不能将它作为两个连续的正则表达式或类似的东西.API是这样编写的(当然简化):

void apiMethod(final String regex) {
    final String input = 
        "bad:    thing01, thing02, thing03 \n" +
        "good:   thing04, thing05, thing06 \n" +
        "better: thing07, thing08, thing09 \n" +
        "worse:  thing10, thing11, thing12 \n";

    final Pattern pattern = Pattern.compile(regex, Pattern.MULTILINE);

    final Matcher matcher = pattern.matcher(input);

    while (matcher.find()) {
        System.out.println(matcher.group(1));
    }
}
Run Code Online (Sandbox Code Playgroud)

我调用它是这样的:

apiMethod("(thing[0-9]+)");
Run Code Online (Sandbox Code Playgroud)

我希望看到打印出六行,每行04到09,包括一行.到目前为止我还没有成功.我试过的一些东西不起作用:

  • "(事[0-9] +)" - 这匹配所有12件事,这不是我想要的.
  • "^(?:good | better):( thing [0-9] +)" - 这只匹配第4和第7项.
  • "^(?:( ?: good | better):.*)(thing [0-9] +)" - 这只匹配第6和第9项.
  • "(?:(?:^ good:| ^ better:|,)*)(thing [0-9] +)" - 这匹配除1和10之外的所有内容.

还有更多,无法列出.我尝试了各种各样的后视,但无济于事.

我想要的是所有匹配"thing [0-9] +"的字符串,但只包含那些以"good:"或"better:"开头的行.

或者,更一般地说,我想要来自多线模式的多个匹配,但仅来自具有特定前缀的线.

Cas*_*yte 5

您必须使用\G基于模式(在多行模式下):

(?:\G(?!^),|^(?:good|better):)\s*(thing[0-9]+)
Run Code Online (Sandbox Code Playgroud)

\G锚杆力相匹配是连续的,因为它最后一次成功匹配后的位置相匹配.


如果行很短,您也可以使用有限的可变长度lookbehind来做到这一点:

(?<=^(?:good|better):.{0,1000})(thing[0-9]+)
Run Code Online (Sandbox Code Playgroud)