繁体   English   中英

Java中的正则表达式模式失败,但可以正常工作

[英]Regex pattern in java fails but works fine otherwise

我已经实现了一个非常复杂的模式 `,以匹配船号的所有出现。 通过全局不区分大小写的比较,它可以很好地工作。

我使用以下代码在Java中实现相同的功能,但不匹配。 Java正则表达式应该以不同的方式实现吗?

int i = 0;
while (i < elementsArray.size()) {
    System.out.println("List element:"+elementsArray.get(i));
    String theRegex = "(?i)(([Ss]{2}|Ship\\s*(set))\\s*(\\#|Number|No\\.)?\\s*([:=\\-\\n\\'\\s])?\\s*\\d+\\s*(\\W*\\d+\\W?\\s*(to|and)?|(to|and)\\s*\\d+)*)";
    if (elementsArray.get(i).matches(theRegex)) {
        System.out.println("RESULT:");
        String shipsets = "";
        String thePattern = "(?i)(([Ss]{2}|Ship\\s*(set))\\s*(\\#|Number|No\\.)?\\s*([:=\\-\\n\\'\\s])?\\s*\\d+\\s*(\\W*\\d+\\W?\\s*(to|and)?|(to|and)\\s*\\d+)*)";
        Pattern pattern = Pattern.compile(thePattern);
        Matcher matcher = pattern.matcher(elementsArray.get(i));

        if (matcher.find()) {
            shipsets = matcher.group(0);
        }

        System.out.println("text==========" + shipsets);
    }

    i++;
}

假设您的正则表达式在Java中正常工作,这是应该工作的代码的简化。 从我的初步调查来看,它确实与您链接中的许多用例相匹配。 您不需要使用String.matches()因为您已经在使用Matcher ,它将检查您是否有匹配项。

List<String> elementsArray = new ArrayList<String>();
elementsArray.add("Shipset Number 323");
elementsArray.add("meh");
elementsArray.add("SS NO. : 34");
elementsArray.add("Mary had a little lamb");
elementsArray.add("Ship Set #2, #33 to #4.");

for (int i=0; i < elementsArray.size(); ++i) {
    System.out.println("List element:"+elementsArray.get(i));
        String shipsets = "";
        String thePattern = "(?i)(([Ss]{2}|Ship\\s*(set))\\s*(\\#|Number|No\\.)?\\s*([:=\\-\\n\\'\\s])?\\s*\\d+\\s*(\\W*\\d+\\W?\\s*(to|and)?|(to|and)\\s*\\d+)*)";
        Pattern pattern = Pattern.compile(thePattern);
        Matcher matcher = pattern.matcher(elementsArray.get(i));

        if (matcher.find()) {
            shipsets = matcher.group(0);
            System.out.println("Found a match at element " + i + ": " + shipsets);
        }
    }
}

您可以在下面的输出中看到,三个飞船测试字符串都匹配,并且控件"meh""Mary had a little lamb"不匹配。

输出:

List element:Shipset Number 323
Found a match at element 0: Shipset Number 323
List element:meh
List element:SS NO. : 34
Found a match at element 2: SS NO. : 34
List element:Mary had a little lamb
List element:Ship Set #2, #33 to #4.
Found a match at element 4: Ship Set #2, #33 to #4.

我认为您的问题是由以下原因引起的:

  1. 的使用matches()if(elementsArray.get(i).matches(theRegex)) - matches()将返回true只有当整个字符串匹配正则表达式,所以它会在您的例子很多情况下取得成功,但它会失败包括: SS#1,SS#5,SS#6SS1, SS2, SS3, SS4等。您可以通过在正则表达式的开头添加^和在结尾添加$来模拟这种情况。 这里检查它如何匹配。 因此,像在Tim Biegeleisen答案中那样,使用matcher.find()代替String.matches()会是更好的解决方案。
  2. 使用if(matcher.find())而不是while(matcher.find()) -在某些字符串中,您想要检索多个结果,因此您应该多次使用matcher.find()来获取全部他们。 但是, if仅执行一次,那么您将从给定的字符串中仅获取第一个匹配的片段。 要检索所有内容,请使用循环,因为matcher.find()在给定String中找不到下一个匹配项时将返回false ,并结束循环

检查一下 这是Tim Biegeleisen解决方案,变化很小( while ,而不是if )。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM