設計模式(一) 單例模式

2021-08-27 13:46:16 字數 2517 閱讀 9926

小結確保某乙個類只有乙個例項,而且自行例項化並向整個系統提供這個例項。

確保某個類有且只有乙個物件的場景,避免產生多個物件消耗過多的資源。例如:建立乙個物件需要消耗的資源過多,比如io操作、資料庫操作等,這時就要考慮使用單例模式。

public class ehansingleton 

public static ehansingleton getehansingleton()

}

餓漢式單例模式,在沒有使用的時候就初始化了物件,占用資源,並且是執行緒不安全的,不好,不推薦使用。

public class lanhansingleton 

public static synchronized lanhansingleton getlanhansingleton()

return lanhansingleton;

}}

懶漢式單例模式,在getlanhansingleton()方法中新增了synchronized關鍵字,使其變成同步方法,在多執行緒情況下保證物件的唯一性。

dcl,double check lock,雙重檢查鎖定

public class dclsingleton 

public static dclsingleton getdclsingleton() }}

return dclsingleton;

}}

getdclsingleton()方法中,進行了兩次判空:第一層判斷主要是為了避免不必要的同步,第二層則是在null的情況下建立例項。細心的童鞋應該注意到了,在定義dclsingleton時,多了乙個volatile關鍵字,這是幹啥用的?它的作用,是來保證dcl單例模式的正確性,雖然volatile會稍微影響那麼一丟丟的效能。請看下面解釋:

dcl失效問題

上面的例子,假設執行緒a執行到**dclsingleton = new dclsingleton()**語句,這句**最終會被編譯成多條彙編指令,大致做了3件事情:

(1)給dclsingleton的例項分配記憶體;

(2)呼叫dclsingleton()的建構函式,初始化成員字段;

(3)將 dclsingleton 物件指向分配的記憶體空間(此時 dclsingleton 就不是null了)。

解決辦法

jdk1.5之後,調整了jvm,具體化了volatile關鍵字。按照上面例子的寫法,在定義dclsingleton時,加volatile關鍵字,就可以保證dclsingleton物件每次都是從主記憶體中讀取,從而確保了程式的正確性。

public class staticinternalclasssingleton 

public static staticinternalclasssingleton getsingleton()

private static class singletonholder

}

靜態內部類單例模式,在第一次載入staticinternalclasssingleton類時並不會初始化staticinternalclasssingleton,只有在第一次呼叫staticinternalclasssingleton的**getsingleton()**方法時才會初始化。這種方式不僅能夠確保執行緒安全,也能保證單例物件的唯一性,同時也延遲了單例的例項化,所有優點它都佔了,所有,就它了。

public class singletonmanager 

public static void registerservice(string key, object instance)

}public static object getservice(string key)

}

使用容器來管理單例,將多個單例註冊到乙個統一的管理類中,使用key獲取對應的物件,這種方式使得我們可以管理多種型別的單例,並且在使用時可以通過統一的介面進行獲取操作,降低使用者的使用成本,隱藏了具體實現,降低了耦合度。

1.由於單例模式在記憶體中只有乙個例項,減少了記憶體開支,特別是乙個物件需要頻繁的建立、銷毀時,而且建立或銷毀是效能又無法優化,單例模式的優勢就非常明顯了。

2.由於單例模式只生成乙個例項,減少了系統的效能開銷,當乙個物件的產生需要比較多的資源時,如讀取配置、產生其他依賴物件時,則可以通過在應用啟動時直接產生乙個單例物件,然後用永久駐留記憶體的方式來解決。

3.單例模式可以避免對資源的多重占用,例如乙個寫檔案操作,由於只有乙個例項存在記憶體中,避免對同乙個資源檔案的同時寫操作。

4.單例模式可以在系統設定全域性的訪問點,優化和共享資源訪問。

1.單例模式一般沒有介面,擴充套件很困難。

設計模式 一 單例模式

思路 1 如果其他程式能夠隨意用new建立該類物件,那麼就無法控制個數。因此,不讓其他程式用new建立該類的物件。2 既然不讓其他程式new該類物件,那麼該類在自己內部就要建立乙個物件,否則該類就永遠無法建立物件了。3 該類將建立的物件對外 整個系統 提供,讓其他程式獲取並使用。步驟 1 將該類中的...

設計模式(一) 單例模式

這種模式只涉及到乙個單一的類,該類負責建立自己的物件,並確保只建立乙個物件。單例只有乙個例項 單例類必須建立自己唯一的例項 單例類必須給其他物件提供這唯一的例項 由於當今的程式設計模型都是基於多執行緒方式,因此此處只介紹執行緒安全的幾種實現。第一次被呼叫時才建立物件,屬於懶載入 lazy init ...

設計模式(一) 單例模式

單例模式 保證執行記憶體中只有乙個實體的實現模式就是單例模式,最常見的有餓漢模式 懶漢模式兩種。餓漢模式 package com.madg.design.singleton public class hungry public hungry getinstance 懶漢模式 package com....