如何在Matcher组上追加替换而不是整个模式?

cot*_*aws 24 java regex append matcher

我正在使用一个while(matcher.find())循环遍历模式的所有匹配.对于它找到的那个模式的每个实例或匹配,我想matcher.group(3)用一些新文本替换.这个文本对于每个文本都是不同的,所以我用它matcher.appendReplacement()来重建原始字符串并进行新的更改.但是,appendReplacement()替换整个模式而不仅仅是组.

我怎么能这样做但只修改匹配的第三组而不是整个模式?

这是一些示例代码:

Pattern pattern = Pattern.compile("THE (REGEX) (EXPRESSION) (WITH MULTIPLE) GROUPS");
Matcher matcher = pattern.matcher("THE TEXT TO SEARCH AND MODIFY");
StringBuffer buffer = new StringBuffer();

while(matcher.find()){
   matcher.appendReplacement(buffer, processTheGroup(matcher.group(3));
}
Run Code Online (Sandbox Code Playgroud)

但我想做这样的事情(显然这不起作用).

...
while(matcher.find()){
   matcher.group(3).appendReplacement(buffer, processTheGroup(matcher.group(3));
}
Run Code Online (Sandbox Code Playgroud)

像这样的东西,它只取代某个组,而不是整个模式.

编辑:更改了正则表达式示例,以显示并非所有模式都已分组.

War*_*ren 32

我看到这已经有了一个公认的答案,但它并不完全正确.正确的答案似乎是这样的:

.appendReplacement("$1" + process(m.group(2)) + "$3");
Run Code Online (Sandbox Code Playgroud)

这也说明了"$"是.appendReplacement中的特殊字符.因此,您必须注意"process()"函数,将所有"$"替换为"\ $".Matcher.quoteReplacement(replacementString)会为你做这件事(感谢@Med)

如果组1或组3碰巧包含"$",则先前接受的答案将失败.你最终会得到"java.lang.IllegalArgumentException:Illegal group reference"

  • 为了解决这个`$`问题,`Matcher.quoteReplacement(replacementString)`很好地解决了这个问题. (12认同)

pol*_*nts 17

假设您的整个模式匹配"(prefix)(infix)(suffix)",分别将3个部分捕获到组1,2和3中.现在让我们假设您只想替换第2组(中缀),使前缀和后缀保持原样.

然后你做的是你追加group(1)匹配(未改变),新替换group(2)group(3)匹配(未改变)的东西,所以这样的事情:

matcher.appendReplacement(
    buffer,
    matcher.group(1) + processTheGroup(matcher.group(2)) + matcher.group(3)
);
Run Code Online (Sandbox Code Playgroud)

这仍将匹配并替换整个模式,但由于组1和3保持不变,实际上只有中缀被替换.

您应该能够针对您的特定方案调整相同的基本技术.