2017114--單例模式的實(shí)現(xiàn)方式

PS:這是一個(gè)小白的學(xué)習(xí)記錄之路。大神看見不要笑,獅虎看見不要生氣的哈。

題目:?jiǎn)卫J降膶?shí)現(xiàn)方式

解決思路:獅虎說不知道就要問度娘(PS:獅虎,不要打了,疼···我真的不知道單例)

解決步驟:獅虎說不知道就要多學(xué)習(xí)(PS:我認(rèn)真的抄了一遍,獅虎,我真的很認(rèn)真的抄了~)

答案:maybe~可能大概,獅虎·····別·····打·····我

首先,對(duì)于不懂什么是單例的我來說,java的單例模式是一種常見的設(shè)計(jì)模式。

單例模式定義:確保某個(gè)類只有一個(gè)實(shí)例,而且自行能夠?qū)嵗⑾蛘麄€(gè)系統(tǒng)提供這個(gè)實(shí)例。

可以被設(shè)計(jì)單例模式的對(duì)象:線程池、緩存、日志對(duì)象、對(duì)話框、打印機(jī)、顯卡的驅(qū)動(dòng)程序等或多或少具有資源管理器的功能的對(duì)象

單例的特點(diǎn):

單例類只有一個(gè)實(shí)例;單例類必須自己創(chuàng)建自己的唯一實(shí)例;單例類必須給所有其他對(duì)象提供這一實(shí)例;

單例的模式:餓漢模式;懶漢模式;雙重檢查模式;靜態(tài)內(nèi)部類單例模式;使用容器實(shí)現(xiàn)單例模式

1:餓漢模式:

代碼如下:

public class Singleton {

private static Singleton instance = new? Singleton();

private Singleton(){

}

public static? Singleton getInstance(){

return instance;

}

}

?

PS:此種單例方法,在加載類的時(shí)候已完成實(shí)例化,因此會(huì)加載類的時(shí)間比較慢,調(diào)用此類調(diào)用類方法需要的時(shí)間較短,可避免多線程同步問題。

2:懶漢模式(線程不安全)

public class Singleton {

private static Singleton instance;

private Singleton (){

}

public static Singleton getInstance() {

if (instance == null) {

instance = new Singleton();

}

return instance;

}

}

?

PS:此方法實(shí)現(xiàn)了懶調(diào)用,節(jié)約了資源,但用戶第一次調(diào)用的時(shí)候需要實(shí)例化,反應(yīng)稍慢。在多線程無法正常使用。

3:懶漢模式(安全)

public class Singleton {

private static Singleton instance;

private Singleton (){

}

public static synchronized Singleton getInstance() {

if (instance == null) {

instance = new Singleton();

}

return instance;

}

}

?

PS:這種方法雖然實(shí)現(xiàn)了在多線程可以使用,但是每次調(diào)用getInstance方法時(shí)都需要進(jìn)行同步,造成不必要的同步開銷,而且大部分時(shí)候我們是用不到同步的,所以不建議用這種模式。

4. 雙重檢查模式 (DCL)

public class Singleton {

private volatile static Singleton instance = new? Singleton();

private Singleton(){}

public static? Singleton getInstance(){

if(instance==null){

synchronized (Singleton.class){

if(instance==null){

instance=new Singleton();

}

}

}

return instance;

}

}

PS:此方法在getSingleton方法中對(duì)singleton進(jìn)行了兩次判空,第一次是為了不必要的同步,第二次是在singleton等于null的情況下才創(chuàng)建實(shí)例。DCL優(yōu)點(diǎn)是資源利用率高,第一次執(zhí)行g(shù)etInstance時(shí)單例對(duì)象才被實(shí)例化,效率高。缺點(diǎn)是第一次加載時(shí)反應(yīng)稍慢一些,在高并發(fā)環(huán)境下也有一定的缺陷,雖然發(fā)生的概率很小。DCL雖然在一定程度解決了資源的消耗和多余的同步,線程安全等問題,但是他還是在某些情況會(huì)出現(xiàn)失效的問題,也就是DCL失效。

5. 靜態(tài)內(nèi)部類單例模式

public class Singleton {

private Singleton(){

}

public static? Singleton getInstance(){

return SingletonHolder.sInstance;

}

private static class? SingletonHolder{

private static final Singleton? sInstance=new? Singleton();

}

}

PS:第一次加載Singleton類時(shí)并不會(huì)初始化sInstance,只有第一次調(diào)用getInstance方法時(shí)虛擬機(jī)加載SingletonHolder 并初始化sInstance ,這樣不僅能確保線程安全也能保證Singleton類的唯一性,推薦使用此種單例模式。

6. 枚舉單例

public enum Singleton {

INSTANCE;

public void doSomeThing() {

}

}??

PS:默認(rèn)枚舉實(shí)例的創(chuàng)建是線程安全的,并且在任何情況下都是單例

PS:杜絕單例對(duì)象被反序列化是重新生成對(duì)象代碼

private Object readResolve() throws ObjectStreamException{

return singleton;

}

7:使用容器實(shí)現(xiàn)單例模式

public class SingletonManager{private static MapobjMap=new HashMap();

private Singleton(){

}

private static void? registerService( String key,? Object instance){

if(!objMap.containsKey(key)){

objMap.put(key, instance) ;

}

}

public static? Object getService(String key){

return objMap.get(key);

}

}

PS:用SingletonManager 將多種的單例類統(tǒng)一管理,在使用時(shí)根據(jù)key獲取對(duì)象對(duì)應(yīng)類型的對(duì)象。這種方式使得我們可以管理多種類型的單例,并且在使用時(shí)可以通過統(tǒng)一的接口進(jìn)行獲取操作,降低了用戶的使用成本,也對(duì)用戶隱藏了具體實(shí)現(xiàn),降低了耦合度。

?

?

PS:好多好多,筆記先記在這里,后面續(xù)繼續(xù)理解記憶。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容