這六個問題是每個 Java 開發者必須徹底搞懂的基石。若自以為超越初學者卻不甚理解,請重回初學者行列重新審視。
String s = "Hello world!";
誤區:以為聲明了一個內容為 "Hello world!" 的 String 對象。
真相:聲明的是一個引用變量,名為 s,類型為 String,當前指向 字符串常量池中 "Hello world!" 這個對象。
驗證:
String string = s; // 僅創建新引用,指向同一對象,無新對象產生
==:比較變量值是否相等。基本類型比值,引用類型比內存地址。equals():比較對象內容是否相等,由類創建者定義邏輯。String a = new String("foo");
String b = new String("foo");
a == b; // false (兩個不同對象,地址不同)
a.equals(b); // true (String 重寫 equals 比較字符序列)
Object 默認 equals() 使用 ==。未重寫 equals 的類,equals 行為同 ==。使用基於雜湊的集合 (HashSet/Map/Table) 時,務必確認類的 equals/hashCode 契約。
String 為不可變類。
String s = "Hello"; s = s + " world!"; 實際發生:
1. 原對象 "Hello" 保持不變。
2. s 重新指向新對象 "Hello world!"。
3. 原對象若無其他引用,變為垃圾待回收。
性能啟示:頻繁修改字符串用 String 會產生大量臨時對象,應改用 StringBuffer/StringBuilder。
最佳實踐:s = "Initial Value"; 而非 new String("Initial Value")。字符串常量池保證同內容常量共享同一對象;new 總創建新對象。
Integer 緩存等依賴不可變性。StringBuilder。
理解引用語義、比較機制、不可變性,能避免 90% 字符串相關坑,寫出高效、正確、可維護的代碼。