使用重复捕获替换正则表达式

时间:2010-05-21 16:41:58

标签: regex capture

我有一张表:

A | 1  
A | 2  
B | 1  
B | 2  
B | 3

我正在尝试将其转换为如下所示:

A { 1 | 2 }  
B { 1 | 2 | 3 }

我已经想出了能够正确匹配的内容我无法弄清楚如何重复捕获。

(A|B)|(\d)(\r\n\1|(\d))*

更新

我意识到这对于某些编程语言来说是相当微不足道的,我希望能够学到更多关于正则表达式的知识。

1 个答案:

答案 0 :(得分:1)

这是一个可能有帮助的Java代码:

    String text =   "A | 1\n" +
                    "A | 2\n" +  
                    "B | 1\n" +
                    "B | 2\n" +
                    "B | 3\n" +
                    "A | x\n" +
                    "D | y\n" +
                    "D | z\n";
    String[] sections = text.split("(?<=(.) . .)\n(?!\\1)");
    StringBuilder sb = new StringBuilder();
    for (String section : sections) {
        sb.append(section.substring(0, 1) + " {")
          .append(section.substring(3).replaceAll("\n.", ""))
          .append(" }\n");
    }
    System.out.println(sb.toString());

打印:

A { 1 | 2 }
B { 1 | 2 | 3 }
A { x }
D { y | z }

我们的想法是分两步完成:

  • 首先,分为几个部分
  • 然后转换每个部分

单个replaceAll变体

如果您在要捕获的输入中散布{},以便可以在输出中重新排列,则可以使用单个replaceAll(即 < em>完全正则表达式 解决方案)

String text =   "{ A | 1 }" +
                "{ A | 2 }" +
                "{ B | 1 }" + 
                "{ B | 2 }" +
                "{ B | 3 }" +
                "{ C | 4 }" +
                "{ D | 5 }";
System.out.println(
    text.replaceAll("(?=\\{ (.))(?<!(?=\\1).{7})(\\{)( )(.) .|(?=\\}. (.))(?:(?<=(?=\\5).{6}).{5}|(?<=(.))(.))", "$4$3$2$7$6")
);

打印(see output on ideone.org):

A { 1 | 2 } B { 1 | 2 | 3 } C { 4 } D { 5 }

不幸的是,不,我认为这不值得解释。对于正在完成的事情来说,这太复杂了。实质上,很多断言,嵌套断言和捕获组(其中一些将是空字符串,具体取决于哪个断言通过)。

毫无疑问,这是我写过的最复杂的正则表达式。