Java設計模式——原型模式
概述
原型模式是為瞭解決一些不必要的對象建立過程。當Java JDK中提供了Cloneable介面之後,原型模式就變得異常的簡單了。雖然由於Cloneable的引入使用程式變得更簡單了,不過還是有一些需要說明和注意的東西在裡面的。文本就詳細講解一下這些注意事項吧。
拷貝技術詳解1.對象賦值
如果現在有一個Student對象s1,當我們使用s2=s1的方式對s2進行賦值時,實則是將s1對象的引用複製給了s2。過程如下:
圖-1 對象賦值記憶體分析圖
所以,對於s1與s2它們所指記憶體應該為同一塊地區。下面為此兩個“對象”所佔用的記憶體位址:
[email protected][email protected]
2.淺拷貝
什麼是淺拷貝?淺拷貝後的結果是對象的記憶體位址變化了(對象的引用發生了變化),可對象中包含的對象記憶體則沒有變化。
圖-2 對象拷貝記憶體分析圖
大家看到上面的分析圖是不是有一些疑惑?為什麼name發生了變化,而friends卻沒有變化呢?
這裡先不用說其他的資料類型(int, double, char, short, long, float, byte),我們知道String類型的對象是不可變對象,當我們對不可變對象進行賦值時,它會另外開闢一個新對象。因為這個特性可能會影響到我們對Cloneable的正確判斷,所以這裡需要使用一個可變對象來進行實驗。我選擇的是:List。
假使初始狀態是:s1有兩個朋友,小紅和小梅。當我們使用List的可變性向s2的朋友List中添加了一個新朋友時,理論上只是s2的朋友被修改了,可是實事上並非如此,以下為實驗結果:
初始的List對象:s1.friends: [小紅, 小梅]s2.friends: [小紅, 小梅]不改變List對象:s1.friends: [小紅, 小梅, 小剛]s2.friends: [小紅, 小梅, 小剛]重新對List對象賦值:s1.friends: [小紅, 小梅, 小剛]s2.friends: null
從實驗中我們可以看到如果我們對可變對象進行對象內部的可變操作時,拷貝的對象和被拷貝的對象都會被修改。單從這一點,我們就可以斷定,Cloneable的拷貝屬於淺拷貝。你是不是要問了,那怎麼樣才能實現對象的深拷貝呢?請接著往下看。
3.深拷貝
上面說到對象的淺拷貝,在拷貝中我們對可變對象的操作有一些棘手。而深拷貝則可以解決這個問題。深拷貝的實現要依賴與對象的持久化操作。