【问题标题】:Including comments in Java regular expressions在 Java 正则表达式中包含注释
【发布时间】:2010-11-25 14:30:06
【问题描述】:

我有一些复杂的正则表达式,我需要对其进行注释以提高可读性和维护性。 Java 规范相当简洁,我为此努力了很长时间。我终于发现了我的错误并将其作为答案发布,但我将不胜感激有关维护正则表达式的任何其他建议

作为一个例子,我想在一个简单的名称解析器中注释子组件(模式S):

    String testTarget = "Waldorf T. Flywheel";
    String patternS = "([A-Za-z]+)\\s+([A-Z]\\.)?\\s+([A-Za-z]+)";
    Pattern pattern = Pattern.compile(patternS, Pattern.COMMENTS);
    Assert.assertTrue(pattern.matcher(testTarget).matches());

编辑:我也会感谢 (?x) 格式的示例。

编辑:@geowa4 有一个很好的建议,可以避免嵌入 cmets。由于 java 和其他人已经为嵌入式 cmets 提供了它们在哪些情况下有用? (我想我有一个案例,但我很想看看其他人)。

编辑:如下所述@mikej,正则表达式不支持可选的初始良好,最好是:

        String patternS = "([A-Za-z]+)\\s+([A-Z]\\.\\s+)?([A-Za-z]+)";

但这最终会在初始时提取空间

【问题讨论】:

    标签: java regex comments


    【解决方案1】:

    我发现以下方法有效:

            String pattern2S = 
                "([A-Za-z]+)      # mandatory firstName\n" +
                "\\s+             # mandatory whitespace\n " +
                "([A-Z]\\.)?      # optional initial\n" +
                "\\s+             # whitespace\n " +
                "([A-Za-z]+)      # mandatory lastName\n"; 
    

    关键是在字符串中明确包含换行符 \n

    【讨论】:

    • 这是如何工作的?我刚刚测试了它,它不起作用。
    • 哦,Pattern.COMMENTS 是关键。
    【解决方案2】:

    你为什么不这样做:

    String pattern2S = 
        "([A-Za-z]+)" + //    mandatory firstName
        "\\s+" +        //    mandatory whitespace
        ...;
    

    继续:

    如果您想保留 cmets 的模式并且需要从属性文件中读取它,请使用以下命令:

    pattern=\
    #comment1\\n\
    (A-z)\
    #comment2\\n\
    (0-9)
    

    【讨论】:

    • 好建议。这适用于许多简单的情况,但我希望正则表达式独立于使用它们的代码(例如,在外部数据文件中)。内联 cmets 仍然可见。
    【解决方案3】:

    请参阅Martin FowlerComposedRegex 上的帖子,了解有关提高正则表达式可读性的更多想法。总之,他主张将复杂的正则表达式分解成更小的部分,这些部分可以被赋予有意义的变量名。例如

    String mandatoryName = "([A-Za-z]+)";
    String mandatoryWhiteSpace = "\\s+";
    String optionalInitial = "([A-Z]\\.)?";
    String pattern = mandatoryName + mandatoryWhiteSpace + optionalInitial +
        mandatoryWhiteSpace + mandatoryName;
    

    【讨论】:

    • 谢谢 - 这是一个有用的方法。它还指出了使用域特定语言生成正则表达式的另一个想法 (flimflan.com/blog/ReadableRegularExpressions.aspx)。 (这实际上是我在我的应用程序中所做的,它具有复杂的科学数据正则表达式组合,但这超出了这个问题的范围)。
    • 这是一个非常干净整洁的解决方案。虽然 optionalWhiteSpace 应该可能是强制的WhiteSpace? :)
    • 感谢 crunchdog。我认为让我感到惊讶的是,OP 中的模式实际上存在一个限制,如果我们有一个没有中间首字母的名字,比如 Fred Bloggs,那么我们需要在名字和姓氏之间留 2 个空格来匹配这两个 \ \s+ 在模式中。我试图解决这个问题,但现在我已经编辑了答案以使模式等同于 OP 中的模式。
    • @mikej 谢谢 - 我已经添加了一个请求,可以为任何可以使它更漂亮的人编辑原件
    猜你喜欢
    • 2011-08-19
    • 2013-02-19
    • 2014-07-26
    • 2015-01-25
    • 1970-01-01
    • 2013-08-14
    • 2020-07-08
    • 2014-12-17
    相关资源
    最近更新 更多