原創:轉載需注明原創地址 https://www.cnblogs.com/fanerwei222/p/11683720.html
一直對String不可變感到疑問, 不知為何說String是不可變的, 有人說final, 有人說其字符串不可改變, 但是我始終不能理解字符串不能改變的真正含義, 遂自行琢磨了一番, 也有了自己的一番見解, 希望記錄下來, 日后有新的見解可以隨時修改和比較.
首先final保證String是不可變類(無法被繼承,無法被子類修改破壞其內部狀態), String的屬性也都是final變量, 所以其屬性也是不可被破壞的, 屬性狀態也無法被改變!
然后是String的內部方法處理方式, 對String的操作方法最終都會返回一個新的String對象, 這就直接導致了返回的是一個新的內存地址引用, 而不是將原內存地址引用的那塊內存的值進行修改!(這里就是不可變性重要的地方)
只用文字難免有些枯燥和不好理解, 用代碼說明一下. 用方法和形參的方式更清晰的說明一下同樣的情況普通對象和String對象不同!
/** * 形參變化測試類 */ public class happyTwo { public static void main(String[] args) { User user = new User(); user.name = "zhangsan"; System.out.println(user.name); tryChangeObj(user); System.out.println(user.name); String str = "this is str"; System.out.println(str); tryChangeStr(str); System.out.println(str); } static class User{ public String name; } public static void tryChangeStr(String formStr){ formStr = "hi, this is formStr"; } public static void tryChangeObj(User formUser){ formUser.name = "lisi"; } }
打印信息如下:

來仔細分析一下:
1. 對象user, name屬性的值剛開始是zhangsan, 因為Java是值傳遞的, 所以formUser得到了user的內存地址引用值, 此時, formUser直接指向user指向的那塊內存, formUser修改了該內存的值, user的內容當然也會變化, 相當於他們其實都是該內存的一個快捷方式.
2. 為什么String不會變化呢? 難道formStr拿到的不是str的內存地址引用的值嗎?
formStr拿到的當然也是str的內存地址引用的值, 也就是說在
public static void tryChangeStr(String formStr) 這一行當中, formStr和str指向的內存是一樣的!
變化發生在下面這一行👇👇👇
formStr = "hi, this is formStr";
剛剛我們說了, String的所有修改操作都會直接返回一個新的String, 這一行給formStr賦新的字符串了, 此時formStr指向的內存地址就變成了該字符串的內存地址了, 所以此時formStr和str當然不是同一個對象了, 它兩的值肯定也不會再相同了!
以上就是我的個人理解, 我理解的不可變是最開始初始化String對象后存儲String對象的那塊內存中的值不可變, 而不是String對象的引用地址不能改變, 如果理解有誤, 希望后期自己可以發現並糾正.
