2012-04-12 83 views
2

可能重複:
Difference Between Equals and ==
In JDK 1.6, can String equals operation can be replaced with ==?
How do I compare strings in Java?意外的結果,比較兩個Java的字符串與 「==」 當

雖然與Java的字符串玩耍,我沒想到以下結果:

public class Sandbox { 
    public static void main(String[] args) { 
     String a = "hello"; 
     String b = "hello"; 

     System.out.println(a == b);    //true  Why?, a and b both are seperate Objects 
     System.out.println(a == "hello");  //true  Why? 
     System.out.println(a == new String(b)); //false  As expected 
    } 
} 

我期望所有的都是錯誤的,因爲「==」比較引用。爲什麼會有這個結果

當我更改String b = "world"時,System.out.println(a == b);返回false。看起來好像字符串對象的內容正在被比較。

由於Java 7可以比較switch-case-Statements中的字符串,我認爲它可能與Java版本有關。但是如here所述,在比較Switch-Case中的字符串時會調用equals-Methode。

+0

請閱讀[this](http://stackoverflow.com/questions/971954/difference-between-equals-and)。 – mre 2012-04-12 11:42:43

+0

總之,一些字符串被實現(即緩存)並引用同一個對象,這就解釋了爲什麼==可以工作。但是你不能依賴這種機制,而應該使用equals。 – assylias 2012-04-12 11:45:07

+0

底線是,因爲字符串仍然是對象,所以在絕大多數情況下,您應該使用「equals」方法。 – 2012-04-12 11:49:04

回答

2

JVM執行some trickery,同時實例化字符串文字以提高性能並降低內存開銷。爲了減少在JVM中創建的String對象的數量,String類保留了一個字符串池。每次您的代碼創建字符串文字時,JVM都會首先檢查字符串文字池。如果該字符串已存在於池中,則對池實例的引用將返回。如果字符串不存在於池中,則新的String對象實例化,然後放入池中。 Java可以進行這種優化,因爲字符串是不可變的,可以共享而不用擔心數據損壞。

+3

它被稱爲*字符串interning *,在大多數現代語言中很常見 - http://en.wikipedia.org/wiki/String_interning – 2012-04-12 11:47:37

+0

是的,它已在其他評論中進行了解釋。有些詭計可能會模糊。 – Anonymous 2012-04-12 11:48:03

3

Java始終(從版本1.0開始)interned字符串文字。這意味着常量字符串被添加到池中並且重複引用相同的對象。

final String a = "hello"; 
final String b = "hell"; 
System.out.println(a == b + 'o'); 

這將打印true,因爲編譯器可以內聯並簡化表達b + 'o'至是相同的「你好」。