gpt4 book ai didi

java - 当没有调用 'matching' 方法时,Matcher 抛出 IllegalStateException 的理由

转载 作者:IT老高 更新时间:2023-10-28 21:12:10 28 4
gpt4 key购买 nike

TL;DR

Matcher 背后的设计决策是什么?的API?

背景

Matcher有一种我没有预料到的行为,而且我找不到很好的理由。 API 文档说:

Once created, a matcher can be used to perform three different kinds of match operations: [...] Each of these methods returns a boolean indicating success or failure. More information about a successful match can be obtained by querying the state of the matcher.

API 文档进一步说明的是:

The explicit state of a matcher is initially undefined; attempting to query any part of it before a successful match will cause an IllegalStateException to be thrown.

示例

String s = "foo=23,bar=42";
Pattern p = Pattern.compile("foo=(?<foo>[0-9]*),bar=(?<bar>[0-9]*)");
Matcher matcher = p.matcher(s);
System.out.println(matcher.group("foo")); // (1)
System.out.println(matcher.group("bar"));

这段代码抛出一个

java.lang.IllegalStateException: No match found

(1) 处。为了解决这个问题,有必要调用 matches() 或其他将 Matcher 带入允许 group() 的状态的方法。以下作品:

String s = "foo=23,bar=42";
Pattern p = Pattern.compile("foo=(?<foo>[0-9]*),bar=(?<bar>[0-9]*)");
Matcher matcher = p.matcher(s);
matcher.matches(); // (2)
System.out.println(matcher.group("foo"));
System.out.println(matcher.group("bar"));

将调用添加到 matches()(2)Matcher 设置为适当的状态以调用 group()

问题,可能没有建设性

为什么这个 API 是这样设计的?当 Matcher 是用 Patter.matcher(String) 构建时,为什么不自动匹配?

最佳答案

实际上,您误解了文档。第二次看你引用的陈述:-

attempting to query any part of it before a successful match will cause an IllegalStateException to be thrown.

如果没有找到匹配,匹配器可能会在访问 matcher.group() 时抛出 IllegalStateException

因此,您需要使用以下测试来实际启动匹配过程:-

 - matcher.matches() //Or
- matcher.find()

以下代码:-

Matcher matcher = pattern.matcher();  

只需创建一个 matcher 实例。这实际上不会匹配字符串。哪怕是一场成功的比赛。因此,您需要检查以下条件,以检查是否成功匹配:-

if (matcher.matches()) {
// Then use `matcher.group()`
}

如果 if 中的条件返回 false,则表示没有匹配。所以,如果你使用 matcher.group() 而不检查这个条件,如果没有找到匹配,你会得到 IllegalStateException


假设,如果 Matcher 是按照您所说的方式设计的,那么您必须执行 null 检查以检查是否找到匹配项,然后调用matcher.group(),像这样:-

你认为应该做的方式:-

// Suppose this returned the matched string
Matcher matcher = pattern.matcher(s);

// Need to check whether there was actually a match
if (matcher != null) { // Prints only the first match

System.out.println(matcher.group());
}

但是,如果你想打印任何进一步的匹配,因为一个模式可以在一个字符串中多次匹配,为此,应该有一种方法告诉匹配器找到下一个匹配。但是 null 检查将无法做到这一点。为此,您必须将匹配器向前移动以匹配下一个字符串。因此,在 Matcher 类中定义了各种方法来达到目的。 matcher.find() 方法匹配字符串,直到找到所有匹配项。

还有其他方法,以不同的方式 match 字符串,这取决于您要如何匹配。所以它最终在 Matcher 类上对字符串进行 matchingPattern 类只是创建一个 pattern 来匹配。如果 Pattern.matcher()match 模式,那么必须有一些方法来定义 match 的各种方式,如 matching 可以有不同的方式。所以,就需要 Matcher 类了。

所以,实际上是这样的:-

Matcher matcher = pattern.matcher(s);

// Finds all the matches until found by moving the `matcher` forward
while(matcher.find()) {
System.out.println(matcher.group());
}

因此,如果在字符串中找到 4 个匹配项,您的第一种方式将只打印第一个,而第二种方式将打印所有匹配项,方法是将 matcher 向前移动以匹配下一个模式。

我希望这能说清楚。

Matcher 的文档类描述了它提供的三种方法的使用,其中说:-

A matcher is created from a pattern by invoking the pattern's matcher method. Once created, a matcher can be used to perform three different kinds of match operations:

  • The matches method attempts to match the entire input sequence against the pattern.

  • The lookingAt method attempts to match the input sequence, starting at the beginning, against the pattern.

  • The find method scans the input sequence looking for the next subsequence that matches the pattern.

很遗憾,我找不到任何其他官方来源,明确说明为什么如何这个问题。

关于java - 当没有调用 'matching' 方法时,Matcher 抛出 IllegalStateException 的理由,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12911504/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com