为了比较字符串是否相等,应使用String对象equals或equalsIgnoreCase方法。
例如,以下代码段将确定的两个实例String在所有字符上是否相等:
String firstString = "Test123";
String secondString = "Test" + 123;
if (firstString.equals(secondString)) {
// 这两个字符串具有相同的内容。
}现场演示
本示例将比较它们,而与它们的情况无关:
String firstString = "Test123";
String secondString = "TEST123";
if (firstString.equalsIgnoreCase(secondString)) {
// 两个字符串都是相等的,忽略了各个字符的大小写。
}现场演示
请注意, equalsIgnoreCase不允许您指定Locale。例如,如果您比较两个单词,"Taki"而"TAKI"在英语中它们是相等的;但是,在土耳其语中,它们是不同的(在土耳其语中,小写字母I是ı)。对于这种情况,解决方案是将两个字符串都使用转换为小写(或大写),Locale然后与进行比较equals。
String firstString = "Taki";
String secondString = "TAKI";
System.out.println(firstString.equalsIgnoreCase(secondString)); //打印真实
Locale locale = Locale.forLanguageTag("tr-TR");
System.out.println(firstString.toLowerCase(locale).equals(
secondString.toLowerCase(locale))); //打印错误现场演示
除非您可以保证所有字符串都已被内联(请参见下文),否则您不应使用==或!=运算符来比较字符串。这些运算符实际上测试引用,并且由于多个String对象可以表示同一个String,因此很容易给出错误的答案。
而是使用方法,该方法将根据字符串对象的值进行比较。有关详细说明,请参阅陷阱:使用==比较字符串。String.equals(Object)
从Java 1.7开始,可以将String变量与switch语句中的文字进行比较。确保String不为null,否则它将始终抛出NullPointerException。使用进行比较String.equals,即区分大小写。
String stringToSwitch = "A";
switch (stringToSwitch) {
case "a":
System.out.println("a");
break;
case "A":
System.out.println("A"); //代码在这里
break;
case "B":
System.out.println("B");
break;
default:
break;
}现场演示
将aString与常量值进行比较时,可以将常量值放在的左侧,equals以确保NullPointerException如果另一个String为,则不会得到a null。
"baz".equals(foo)
虽然foo.equals("baz")将抛出NullPointerException,如果foo是null, 将评估到。"baz".equals(foo)false
更具可读性的替代方法是使用,它对两个参数进行空检查。Objects.equals()Objects.equals(foo, "baz")
(注意:通常最好避免NullPointerExceptions,还是让它们发生然后解决根本原因,这是有争议的。请在这里和这里查看。当然,将避免策略称为“最佳实践”是没有道理的。)
的String类实现Comparable<String>与所述String.compareTo方法(在此示例中的开始所描述的)。这使得String对象的自然排序区分大小写。的String类提供一个Comparator<String>称为恒定CASE_INSENSITIVE_ORDER适于不区分大小写的排序。
Java语言规范(JLS 3.10.6)声明以下内容:
“此外,一个字符串总是指类的同一实例String这是因为字符串文字-或,更一般地,字符串是常量表达式的值-被拘留以便共享独特实例,使用方法String.intern”。
这意味着它是安全的引用比较两个字符串文字使用==。此外,对于String使用该方法生产的对象的引用也是如此。String.intern()
例如:
String strObj = new String("Hello!");
String str = "Hello!";
// 两个字符串引用指向两个相等的字符串
if (strObj.equals(str)) {
System.out.println("The strings are equal");
}
// 这两个字符串引用没有指向同一对象
if (strObj != str) {
System.out.println("The strings are not the same object");
}
// 如果我们内联等于给定文字的字符串,则结果为
// 与文字具有相同引用的字符串。
String internedStr = strObj.intern();
if (internedStr == str) {
System.out.println("The interned string and the literal are the same object");
}在幕后,内部机制维护一个哈希表,该表包含所有仍可到达的内部字符串。调用intern()时String,该方法在哈希表中查找对象:
如果找到该字符串,则该值作为实习字符串返回。
否则,将字符串的副本添加到哈希表中,并将该字符串作为实习字符串返回。
可以使用interning允许使用比较字符串==。但是,这样做存在很大的问题。请参阅陷阱-中断字符串,以便可以使用==获取详细信息,这是个坏主意。在大多数情况下不建议这样做。