String.equals versus ==
此代码将一个字符串分隔成标记,并将它们存储在一个字符串数组中,然后将变量与第一个主变量进行比较…为什么不起作用?
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 | public static void main(String...aArguments) throws IOException { String usuario ="Jorman"; String password ="14988611"; String strDatos ="Jorman 14988611"; StringTokenizer tokens = new StringTokenizer(strDatos,""); int nDatos = tokens.countTokens(); String[] datos = new String[nDatos]; int i = 0; while (tokens.hasMoreTokens()) { String str = tokens.nextToken(); datos[i] = str; i++; } //System.out.println (usuario); if ((datos[0] == usuario)) { System.out.println("WORKING"); } } |
使用
函数检查字符串的实际内容,
1 2 3 | if (usuario.equals(datos[0])) { ... } |
注意:比较是在"usuario"上完成的,因为在代码中保证不为空,尽管您仍然应该检查在
认识乔曼
乔曼是一个成功的商人,有两栋房子。
。
但其他人不知道。
是同一个乔曼吗?当你问麦迪逊街或伯克街的邻居时,他们唯一能说的就是:
氧化镁
单独使用住所,很难确认这是同一个乔曼。因为他们是两个不同的地址,所以很自然地假设他们是两个不同的人。
这就是操作员
如果我们派了一个调查员怎么办?我们知道这是同一个乔曼,但我们需要证明这一点。我们的侦探会仔细观察身体的各个方面。经过彻底的调查,代理人将能够断定是否是同一个人。让我们看看它发生在Java术语。
下面是string的
氧化镁
它逐字比较字符串,以得出它们确实相等的结论。
这就是字符串
值得注意的是,在某些情况下,使用"=="运算符可以得到预期的结果,因为在编译过程中如何处理Java字符串-字符串文本(参见EDCOX1 OR 7)。因此,当您在两个类中编写EDCOX1 OR 8表示,并将这些字符串与"=="比较时,可以得到结果:true,这是预期的。根据规范,当您比较相同的字符串(如果它们具有相同的值)时,第一个字符串是字符串文字(即通过
唯一正确的方法是使用
更新:2013年4月1日我更新了这篇文章,下面的评论是正确的。最初我声明interning(string.intern)是JVM优化的副作用。虽然它确实节省了内存资源(这就是我所说的"优化"),但它主要是语言的特性。
考虑程序
1 2 3 4 5 |
这里的
1 2 3 4 5 6 7 8 9 10 11 12 | String abc ="Hello World"; String xyz ="Hello World"; if(abc == xyz) System.out.println("Refers to same string"); else System.out.println("Refers to different strings"); if(abc.equals(xyz)) System.out.prinln("Contents of both strings are same"); else System.out.prinln("Contents of strings are different"); |
。
这里,
希望你能理解
谢谢。
而不是
1 | datos[0] == usuario |
号
使用
1 | datos[0].equals(usuario) |
因此,如果您实际想要测试两个字符串是否具有相同的值,则应使用
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | // These two have the same value new String("test").equals("test") ==> true // ... but they are not the same object new String("test") =="test" ==> false // ... neither are these new String("test") == new String("test") ==> false // ... but these are because literals are interned by // the compiler and thus refer to the same object "test" =="test" ==> true // concatenation of string literals happens at compile time resulting in same objects "test" =="te" +"st" ==> true // but .substring() is invoked at runtime, generating distinct objects "test" =="!test".substring(1) ==> false |
需要注意的是,
1 2 | The == operator checks if the two references point to the same object or not. .equals() checks for the actual string content (value). |
注意,.equals()方法属于类对象(所有类的超级类)。您需要根据类需求重写它,但是对于字符串,它已经实现,并且它检查两个字符串是否具有相同的值。
1 2 3 4 5 6 7 8 9 10 11 12 | Case1) String s1 ="Stack Overflow"; String s2 ="Stack Overflow"; s1 == s1; // true s1.equals(s2); // true Reason: String literals created without null are stored in the string pool in the permgen area of the heap. So both s1 and s2 point to the same object in the pool. Case2) String s1 = new String("Stack Overflow"); String s2 = new String("Stack Overflow"); s1 == s2; // false s1.equals(s2); // true Reason: If you create a String object using the `new` keyword a separate space is allocated to it on the heap. |
。
如果在将字符串插入数组之前对其调用
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | public static void main (String... aArguments) throws IOException { String usuario ="Jorman"; String password ="14988611"; String strDatos="Jorman 14988611"; StringTokenizer tokens=new StringTokenizer(strDatos,""); int nDatos=tokens.countTokens(); String[] datos=new String[nDatos]; int i=0; while(tokens.hasMoreTokens()) { String str=tokens.nextToken(); datos[i]= str.intern(); i++; } //System.out.println (usuario); if(datos[0]==usuario) { System.out.println ("WORKING"); } |
。
让我们分析下面的Java,了解字符串的身份和相等性:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 | public static void testEquality(){ String str1 ="Hello world."; String str2 ="Hello world."; if (str1 == str2) System.out.print("str1 == str2 "); else System.out.print("str1 != str2 "); if(str1.equals(str2)) System.out.print("str1 equals to str2 "); else System.out.print("str1 doesn't equal to str2 "); String str3 = new String("Hello world."); String str4 = new String("Hello world."); if (str3 == str4) System.out.print("str3 == str4 "); else System.out.print("str3 != str4 "); if(str3.equals(str4)) System.out.print("str3 equals to str4 "); else System.out.print("str3 doesn't equal to str4 "); } |
当第一行代码
运算符
代码
因此,输出包含四行:
1 2 3 4 5 6 7 | Str1 == str2 Str1 equals str2 Str3! = str4 Str3 equals str4 |
号
应该使用string equals来比较两个字符串是否相等,而不是运算符==来比较引用。
EDCOX1·6×操作符比较Java中对象的引用。您可以使用字符串的
一般情况下,
用于参考比较的
如果要比较字符串的任何赋值,即基元字符串,则"=="和.equals都有效,但对于新的字符串对象,只应使用.equals,此处"=="将无效。
例子:
。
但是
在这种情况下,
所以最好使用
==运算符是对值的简单比较。对于对象引用,(值)是(引用)。因此,如果x和y引用同一个对象,x==y返回true。
@Melkhiah66可以使用Equals方法而不是"=="方法来检查相等性。如果使用intern(),则它检查对象是否在池中如果存在,则返回相等或不相等。Equals方法在内部使用哈希代码并获取所需的结果。埃多克斯1〔33〕
我知道这是一个古老的问题,但下面是我如何看待它(我觉得非常有用):
技术说明
在Java中,所有变量都是基元类型或引用。
(如果需要知道引用是什么,"对象变量"只是指向对象的指针。所以对于
有趣的部分:
那么,为什么
因为字符串是不可变的(当您调用
1 | if (foo == bar) ... |
号
紧接着,它们指向同一个对象,并将返回true。但你很少打算这么做。相反,您需要的是用户输入,它在内存的不同部分创建新的字符串,等等。
注意:如果您执行类似于
我不知道它在运行时是如何工作的,但是我假设JVM不保存"活动字符串"列表,并且检查是否存在相同的字符串。(例如,如果您读取一行输入两次,而用户输入相同的输入两次,则不会检查第二个输入字符串是否与第一个输入字符串相同,并将它们指向相同的内存)。它可以节省一点堆内存,但是开销是如此微不足道,不值得这样做。同样,关键是编译器很容易优化文本字符串。
给你了……一个关于
埃多克斯1〔8〕
比较引用,而不是值。在对象引用中使用
比较以查看引用是否为
比较两个枚举值。这是因为每个
您想知道两个引用是否指向同一对象
埃多克斯1〔12〕
比较值是否相等。因为此方法是在
有人在高一点的帖子上说,==用于int和检查空值。它还可以用于检查布尔操作和字符类型。
但是要非常小心,并再次检查您使用的是字符而不是字符串。例如
1 2 |
然后检查字符串这是对的
1 2 | if(strType.equals("a") do something |
号
但是
1 2 | if(charType.equals('a') do something else |
可能不正确,您需要执行以下操作
1 2 | if(charType == 'a') do something else |
。
使用split而不是tokenizer,它肯定会提供精确的输出例如:
1 2 3 4 5 6 7 8 9 10 11 12 |
。
在这之后,我相信你会得到更好的结果……