1

我有一个正则表达式,我用它来查找字符串中 <> 之间的逗号分隔单词列表的匹配项,就像"Hello <a1> sqjsjqk <b1,b2> dsjkfjkdsf <c1,c2,c3> ffsd"在示例中一样

我想使用捕获组来保留大括号之间的每个单词:

这是我的表达:(< (\w+) (?: ,(\w+) )* >添加空格是为了便于阅读,但不是模式的一部分)

括号用于创建捕获组,(?: )用于创建非捕获组,因为我不想保留昏迷。

这是我的测试代码:

@Test
public void test() {
    String patternString = "<(\\w+)(?:,(\\w+))*>";
    Pattern pattern = Pattern.compile(patternString);
    Matcher matcher = pattern.matcher("Hello <a1> sqjsjqk <b1,b2> dsjkfjkdsf <c1,c2,c3> ffsd");
    while(matcher.find()) {
        System.out.println("== Match ==");
        MatchResult matchResult = matcher.toMatchResult();
        for(int i = 0; i < matchResult.groupCount(); i++) {
            System.out.println("  " + matchResult.group(i + 1));
        }
    }
}

这是产生的输出:

== Match ==
  a1
  null
== Match ==
  b1
  b2
== Match ==
  c1
  c3

这就是我想要的:

== Match ==
  a1
== Match ==
  b1
  b2
== Match ==
  c1
  c2
  c3

由此我了解到,在我的表达式中,组的数量与捕获组的数量一样多,但这不是我想要的,因为我需要所有被识别为 \w+

有没有机会用一个 RegExp 得到我想要的东西,或者我应该用 , 等来完成split(",")工作trim()......

4

1 回答 1

2

据我所知,.NET 有唯一的正则表达式引擎,它可以为单个捕获组返回多个捕获。所以你所要求的在 Java 中是不可能的(至少不是你要求的方式)。

但是,在您的情况下,这个问题可以在一定程度上得到解决。如果您可以确定永远不会有无与伦比的收盘>,您可以制作您想要捕获完整匹配的东西,并通过前瞻要求正确的位置:

"\\w+(?=(?:,\\w+)*>)"

这永远无法匹配外部的“单词” <...>,因为它们无法通过开头<来匹配结尾>。当然,这使得区分来自不同集合的元素变得困难<...>

或者(我认为这更好,因为它更安全,更易读),采用两步算法。第一场比赛

"<([\\w,]*)>"

然后split每个结果的第一次捕获在,.

于 2012-11-16T20:25:10.470 回答