有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

Java正则表达式匹配任何与给定模式匹配且不在给定字符之间的内容

我有一个对给定字符串应用正则表达式规则的解析器。 每个规则的第一个匹配项将被删除并放置到一个节点中

其中一条规则试图找到变量,这些变量位于仅由数字、字母、下划线和破折号组成的|符号之间。 实现这一点的规则如下:(?:\|)[a-zA-Z0-9_-]+(?:\|)+?

例如,我们有一个表达式:part1+250+|part2|+part3 它与变量|part2|匹配

现在我需要另一个匹配常量的规则,它只能由(数字、字母、下划线、破折号和空格)组成。 但它应该而不是匹配变量

看看同一个示例表达式,它应该与以下内容匹配: part1250part3 它应该匹配任何字符(数字、字母、空格、下划线、破折号)和|符号之间的

如何使用单个正则表达式实现这一点


共 (1) 个答案

  1. # 1 楼答案

    以下是解决方案的单一模式实现:

    String input = "part1+250+|part2|+part3";
    
    Pattern p = 
    //                   | group 1 ("variable")
    //                   | | positive look behind for "|"
    //                   | |      | character class for allowed characters
    //                   | |      |             | quantifier for 1+ instance, greedy
    //                   | |      |             | | positive lookahead for "|"
    //                   | |      |             | |      | OR
    //                   | |      |             | |      || group 2 ("constant") 
    //                   | |      |             | |      ||| negative lookbehind for "|"
    //                   | |      |             | |      |||       | allowed chars
    //                   | |      |             | |      |||       |             | quantifier
    //                   | |      |             | |      |||       |             | | negative
    //                   | |      |             | |      |||       |             | | lookahead
    //                   | |      |             | |      |||       |             | | 
        Pattern.compile("((?<=\\|)[ a-zA-Z0-9_-]+(?=\\|))|((?<!\\|)[ a-zA-Z0-9_-]+(?!\\|))");
    Matcher m = p.matcher(input);
    while (m.find()) {
        System.out.printf("Variable: %s%nConstant: %s%n", m.group(1), m.group(2));
    }
    

    输出

    Variable: null
    Constant: part1
    Variable: null
    Constant: 250
    Variable: part2
    Constant: null
    Variable: null
    Constant: part3
    

    注释

    • 在这里,它打印所有内容,但您当然可以检查null并推断是否找到了“变量”、“常量”或什么都没有
    • 这里有一个快速解决方案,所以可能没有涵盖边缘情况
    • 这里的分组是为了向后兼容而设计的Java6。不过,Java7的命名组要有趣得多