Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/392.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java pattern.matcher()与pattern.matches()的比较_Java_Regex - Fatal编程技术网

Java pattern.matcher()与pattern.matches()的比较

Java pattern.matcher()与pattern.matches()的比较,java,regex,Java,Regex,我想知道,当提供相同的正则表达式和相同的字符串时,为什么java正则表达式pattern.matcher()和pattern.matches()的结果不同 String str = "hello+"; Pattern pattern = Pattern.compile("\\+"); Matcher matcher = pattern.matcher(str); while (matcher.find()) { System.out.println("I found the text

我想知道,当提供相同的正则表达式和相同的字符串时,为什么java正则表达式pattern.matcher()和pattern.matches()的结果不同

String str = "hello+";
Pattern pattern = Pattern.compile("\\+");
Matcher matcher = pattern.matcher(str);

while (matcher.find()) {
    System.out.println("I found the text " + matcher.group() + " starting at " 
        + "index " + matcher.start() + " and ending at index " + matcher.end());
}

System.out.println(java.util.regex.Pattern.matches("\\+", str));
上述结果如下:

I found the text + starting at index 5 and ending at index 6
false
我发现在
匹配(“.\\+”
模式的情况下,使用表达式匹配完整字符串效果很好。matcher(string s)
返回可以在字符串
s
中查找模式的
匹配器<代码>模式。匹配(字符串str)
测试整个字符串(
str
)是否与模式匹配

简言之(请记住区别):

  • pattern.matcher
    -测试字符串是否包含-a模式
  • pattern.matches
    -测试字符串是否为-a模式
Matcher.find()尝试查找与模式匹配的输入序列的下一个子序列

Pattern.matches(字符串regex,字符序列输入)
将regex编译成
Matcher
并返回
Matcher.matches()

Matcher.matches
尝试根据模式(Regex)匹配整个区域(字符串)


因此,在您的例子中,
Pattern.matches(“\\+”,str)
返回一个false,因为
str.equals(“+”)是false。

Pattern.matches正在测试整个字符串,在您的例子中,您应该使用:

 System.out.println(java.util.regex.Pattern.matches(".*\\+", str));

表示Javadoc中的任何字符串和+符号,请参见if(且仅当)整个区域部分

/**
*尝试根据图案匹配整个区域。
*
*如果匹配成功,则可以通过
*开始、结束和分组方法

* *@return true当且仅当整个区域序列 *匹配此匹配器的模式 */ 公共布尔匹配(){ 返回匹配(from,ENDANCHOR); }

所以,如果您的字符串只是“+”,您将得到一个真实的结果。

我认为您的问题应该是“我应该何时使用
模式.matches()
方法?”,答案是“从不”。您是否希望它像.NET的
matches
方法一样返回匹配的子字符串数组?这是一个完全合理的期望,但不,Java没有这样的期望

如果您只想进行快速而不精确的匹配,请在正则表达式的两端添加
*
,并使用字符串自己的
matches()
方法:

System.out.println(str.matches(".*\\+.*"));

如果您想提取多个匹配项,或者在之后访问有关匹配项的信息,请创建一个Matcher实例并使用其方法,就像您在问题中所做的那样
Pattern.matches()。也就是说,它检查整个字符串是否为paten。
从概念上看,它会在模式的开头隐式地添加一个“^”,在模式的结尾隐式地添加一个$

对于String str=“hello+”,如果希望matches()返回true,则需要具有类似“\+”的模式

我希望这回答了你的问题

Matcher matcher = pattern.matcher(text);
在这种情况下,将返回matcher对象实例,该实例通过解释模式对输入文本执行匹配操作。然后我们可以使用,
matcher.find()
来匹配输入文本中的模式数量

(java.util.regex.Pattern.matches("\\+", str))

这里,将隐式创建matcher对象,并返回一个布尔值,该布尔值将整个文本与模式匹配。这与字符串中的
str.matches(regex)
函数的工作原理相同。

java.util.regex.Pattern.matches(“\\\+”,str)
等效的代码是:

Pattern.compile("\\+").matcher(str).matches();

方法
find
将查找字符串中第一个出现的模式。

实际上,
find()
是不同之处。匹配器本身不是-
Matcher.matches()
仍然返回false@Bozho是的,我知道。但是,由于OP正在比较一个返回
Matcher
实例的方法和另一个返回布尔值的方法,并想知道为什么它们的结果不具有可比性,我决定写一个简单的答案,因为我知道我无法在SCJP考试中用它得分;-)您还掩盖了
Pattern.matches
是一种静态方法这一事实。尝试在没有参数的情况下调用
pattern.matches()
pattern
pattern
的一个实例),您的代码甚至不会编译。这个答案有误导性,
pattern.matcher
不会测试字符串是否包含该模式,它会将整个字符串与该模式匹配,因此,与
“hello world”
匹配的
\w+
将为false,即使
“hello world”
包含与
\w+
匹配的子字符串。实际的区别在于静态性以及正则表达式的编译发生在哪里。这太尴尬了,让我来尝试解决这个问题。如果目标字符串是
hello+world
,这取决于需要。在这种情况下,它将是:System.out.println(java.util.regex.Pattern.matches(“.\\\\+*”,str));这就是我一直在寻找的行为,它完全像
String.matches(“regex”)
那样,只不过对于大型迭代来说要快得多。我发现它违反直觉,与其他语言不匹配。我经常在objective-c/java/swift/c#/vb.net之间移植代码。在我使用的所有其他语言中(据我记忆所及),速记语法搜索第一次出现的模式,从不尝试匹配整个字符串。毕竟,它会产生有时很难注意到的错误。
Pattern.compile("\\+").matcher(str).matches();