設計模式之Singleton(單態)
板橋裡人
http://www.jdon.com 2002/05/07
定義
:
Singleton模式主要作用是保證在Java應用程式中,一個類Class只有一個執行個體存在。
如何使用?
第一種形式:
public class Singleton {<br />// Early initialization.定義的時候就初始化(不推薦)。<br />private static Singleton s = new Singleton();<br />private Singleton() {<br />}<br />public static Singleton getInstance() {<br />return s;<br />}<br />}
第二種形式:
public class Singleton {<br />private static Singleton s;<br />private Singleton() {<br />}<br />// Lazy initialization. 延遲初始化,使用的時候再初始化,效率較高(推薦)。<br />public static Singleton getInstance() {<br />if (s == null) {<br />s = new Singleton();<br />}<br />return s;<br />}<br />}
實現的關鍵:
1. 將所有的建構函式都設為private
,而且必須顯示的指定建構函式(不能設定為預設的,因為預設建構函式是package存取權限)。
2. 注意clone()方法。
例如, 如果基類實現了cloneable介面的話,子類就應該重寫該方法。當然,在應用中應該靈活運用各種方法來防止clone()的各種情況。
@Override<br />protected Object clone() throws CloneNotSupportedException {<br />throw new CloneNotSupportedException();<br />}
多線程調用singleton方法:
如果在網路編程中,要注意多線程訪問singleton引發的一系列問題:
public class Singleton {<br />private static Singleton s;<br />private Singleton() {<br />}<br />// 如果多個線程同時訪問, 有可能會出現多個執行個體。<br />public static Singleton getInstance() {<br />// 第一次初始化時,多個線程同時執行"if (s == null)",判斷結果都為真,所以都會執行下面的操作:"s = new Singleton()",由此引發多個執行個體的出現。<br />if (s == null) {<br />s = new Singleton();<br />}<br />return s;<br />}<br />}<br />
解決方案1(不推薦):
public class Singleton {<br />private static Singleton s;<br />private Singleton() {<br />}<br />// 將該方法加上synchronized關鍵字。這種方法確實能解決問題,但效率不是很高。因為每次調用該方法的時候,都需要阻塞該方法,但事實上只有第一次初始化的時候才會出現這種情況,所以......<br />public static synchronized Singleton getInstance() {<br />if (s == null) {<br />s = new Singleton();<br />}<br />return s;<br />}<br />}
上面方法的改進版:
解決方案2(推薦
):
public class Singleton {<br />private static Singleton singleton;<br />private Singleton() {<br />}<br />public static Singleton getInstance() {<br />if (singleton == null) {<br />synchronized (Singleton.class) {<br />if (singleton == null) {<br />singleton = new Singleton();<br />}<br />}<br />}<br />return singleton;<br />}<br />}