定義:確保一個類只有一個執行個體,並提供全域訪問點。
剖析經典單件模式實現:
public class Singleton<br />{<br /> //利用一個靜態變數來記錄Singleton類的唯一執行個體.<br /> private static Singleton uniquInstance;</p><p> //這裡是其他的有用執行個體化變數。並沒有真正寫出來。<br /> //把構造器聲明為私人的,只有自Singleton類內才可以調用構造器<br /> private Singleton()<br /> {<br /> //用getInstance()方法執行個體化對象,並返回這個執行個體.<br /> public static Singleton getInstance()<br /> {<br /> if(uniquInstance==null)<br /> {<br /> uniqueInstance=new Singleton();<br /> }<br /> return uniqueInstance;<br /> }<br /> }<br />}
注意:這段代碼其中還是一些小問題,那就是當執行的環境是單線程的時候,可以確保只執行個體化一個對象。
而多線程的環境中呢?
再看下面這段代碼。
處理多線程:
public class Singleton<br />{<br /> private static Singleton uniquInstance;</p><p> private Singleton()<br /> {<br /> /*通過增加synchronized關鍵字到getInstance()方法中,我們迫使每個線程在進入這個方法之前,要先等候到別的線程離開這個方法,這樣就不會出現兩個線程同時訪問這個方法的情況了。*/<br /> public static synchronized Singleton getIntance()<br /> {<br /> if(uniquInstance==null)<br /> {<br /> uniquInstance=new Singleton();<br /> }<br /> return uniquInstance;<br /> }<br /> }<br />}
雖然上面這段改良的代碼可以實現只能建立一個執行個體,可是每次都線程同步一次的話,這樣也太消耗效能了。
所以就有了下面最終版代碼 :
public class Singleton<br />{<br /> /*這裡volatile關鍵字確保當uniquInstance變數被初始化成Singleton執行個體時,多個線程正確地處理uniquInstance變數。*/<br /> private volatile static Singleton uniquInstance;<br /> private Singleton()<br /> {<br /> public static Singleton getInstance()<br /> {<br /> if(uniqueInstance==null)<br /> {<br /> synchornized(Singleton.class)<br /> {<br /> if(uniqueInstance==null)<br /> {<br /> uniqueInstance = new Singleton();<br /> }<br /> }<br /> }<br /> return uniqueInstance;<br /> }<br /> }<br />}