使用Positive Lookbehind发生意外的正则表达式行为

时间:2013-04-05 08:48:20

标签: java regex

我正在写一个正则表达式来匹配一个数字序列,然后是一个点然后是另一个数字序列,并且在总长度上,包括点,整个序列应该是13.为此,正则表达式我写的是:(\d{6,12})\.(\d{0,6})(?<=.{13})

当我针对以下两个数据样本运行此表达式时,我期望只匹配第二个,但相反,两者都是匹配的。谁能帮我理解为什么?

  • 1234567.123456&gt;匹配,但我期待它不匹配;
  • 1234567.12345&gt;匹配。

以下是我用来测试它的Java代码:     import java.util.regex.Pattern;

public class App {
    public static void main(String[] args) {
        Pattern matcher = Pattern.compile("(\\d{6,12})\\.(\\d{0,6})(?<=.{13})");
        System.out.println(matcher.matcher("1234567.123456").matches());
        System.out.println(matcher.matcher("1234567.12345").matches());
    }
}

输出:

true
true

3 个答案:

答案 0 :(得分:2)

您需要将lookbehind断言锚定到字符串的开头,否则它将匹配子字符串:

Pattern matcher = Pattern.compile("(\\d{6,12})\\.(\\d{0,6})(?<=^.{13})");

或者使用先行断言(更容易理解,IMO):

Pattern matcher = Pattern.compile("(?=.{13}$)(\\d{6,12})\\.(\\d{0,6})");

答案 1 :(得分:2)

您需要在字符串的开头使用锚点匹配:

"(\\d{6,12})\\.(\\d{0,6})(?<=^.{13})"

答案 2 :(得分:1)

您可能希望在您的lookbehind表达式中添加一个锚点(^):

(?<=^.{13})