單例模式有以下特點:
1、單例類只能有乙個例項。
2、單例類必須自己建立自己的唯一例項。
3、單例類必須給所有其他物件提供這一例項。
單例模式確保某個類只有乙個例項,而且自行例項化並向整個系統提供這個例項。
應用場景: 日誌,資料庫連線池,**技術,多執行緒執行緒池。
//餓漢式單例類.在類初始化時,已經自行例項化
public
class
singleton1
private
static
final singleton1 single =
newsingleton1()
;//靜態工廠方法
public
static singleton1 getinstance()
}
//懶漢式單例類.在第一次呼叫的時候例項化自己
public
class
singleton
private
static singleton single=null;
//靜態工廠方法
public
static singleton getinstance()
return single;
}}
餓漢式就是類一旦載入,就把單例初始化完成,保證getinstance()的時候,單例就已經存在。
懶漢式比較懶,只有當呼叫getinstance的時候,才會去初始化這個單例。
餓漢懶漢區別:
餓漢式是執行緒安全的,懶漢式是執行緒不安全的(即乙個程序內有多個執行緒在在同時使用時可能會產生多個例項,可建立個靜態內部類,產生乙個單例物件,通過靜態內部類返回獲取這個物件)
資源載入和效能問題:餓漢式在類建立的同時就例項化乙個靜態物件出來,所以會佔據一定的記憶體,但是相應的,在第一次呼叫時速度也會更快,因為其資源已經初始化完成,而懶漢式顧名思義,會延遲載入,在第一次使用該單例的時候才會例項化物件出來,第一次呼叫時要做初始化,如果要做的工作比較多,效能上會有些延遲,之後就和餓漢式一樣了。
雙重檢驗鎖
public
static singleton getsingleton()
}}return instance ;
}
這段**看起來很完美,很可惜,它是有問題。主要在於instance = new singleton()這句,這並非是乙個原子操作,事實上在 jvm 中這句話大概做了下面 3 件事情。
給 instance 分配記憶體
呼叫 singleton 的建構函式來初始化成員變數
將instance物件指向分配的記憶體空間(執行完這步 instance 就為非 null 了)
但是在 jvm 的即時編譯器中存在指令重排序的優化。也就是說上面的第二步和第三步的順序是不能保證的,最終的執行順序可能是 1-2-3 也可能是 1-3-2。如果是後者,則在 3 執行完畢、2 未執行之前,被執行緒二搶占了,這時 instance 已經是非 null 了(但卻沒有初始化),所以執行緒二會直接返回 instance,然後使用,然後順理成章地報錯。
我們只需要將 instance 變數宣告成 volatile 就可以了。
public
class
singleton
public
static singleton getsingleton()
}}return instance;
}}
推薦此種方式
public
class
singleton
private singleton (
)public
static
final singleton getinstance()
}
這種寫法仍然使用jvm本身機制保證了執行緒安全問題;由於 singletonholder 是私有的,除了 getinstance() 之外沒有辦法訪問它,因此它是懶漢式的;同時讀取例項的時候不會進行同步,沒有效能缺陷;也不依賴 jdk 版本。
public
enum easysingleton
我們可以通過easysingleton.instance來訪問例項,這比呼叫getinstance()方法簡單多了。建立列舉預設就是執行緒安全的,所以不需要擔心double checked locking,而且還能防止反序列化導致重新建立新的物件。 單例模式的實現
單例設計模式保證類在記憶體中只存在乙個物件。根據不同的策略,單例類的實現有以下幾種方式。1.立即載入 在載入類的同時例項化物件,設計要點如下 1 私有化構造方法 2 宣告並例項化本類物件 靜態 3 提供公有靜態方法獲取物件。code 1 public class eagersingleton oth...
單例模式的實現
單例模式估計是咱們碰到最多也是最簡單的一種設計模式了 也是面試中經常會遇到的面試題 單例模式保證乙個類只有乙個例項,比如咱們在android應用中登入成功之後儲存使用者資訊就會優先考慮單例模式。單例模式有六種常規的寫法 餓漢式 懶漢式 執行緒不安全 懶漢式 執行緒安全 dcl雙重校驗模式 靜態內部類...
單例模式的實現
單例模式的實現需要考慮的因素有很多。對於常常出現的double checked實現單例模式實際上是不安全的實現 private static singleton instance public static singleton getinstance 因為jit可以在singleton的構造方法被執...