設計模式-單例模式

設計模式-單例模式

ID:40388010

大小:16.56 KB

頁數:4頁

時間:2019-08-01

設計模式-單例模式_第1頁
設計模式-單例模式_第2頁
設計模式-單例模式_第3頁
設計模式-單例模式_第4頁
資源描述:

《設計模式-單例模式》由會員上傳分享,免費在線閱讀,更多相關內容在工程資料-天天文庫。

1、設計模式-單例模式為什么需要單例模式有時候我們需要使用一個實用類A,這個類A專門提供一些公共功能供別人調用,而本身并不會處理業(yè)務邏輯。由于類A會被許多類乃至線程調用,假設我們的程序非常龐大,在運行的過程中,會訪問這個類A100次,為了調用類A的方法,需要先創(chuàng)建A的對象,Aa=newA()。這種方法在對A的訪問量較少的情況下沒問題,但是像我們這種情況,就會創(chuàng)建100個類A的實例,這100個實例是要占用內存的,從這種角度來說,就造成了大量不必要的開銷。而單例模式,在整個程序生命周期中,只有一個實例,這樣就不

2、會造成不必要的內存消耗。單例模式的設計為了讓整個生命周期內只有一個實例,我們可以這樣做:publicclassSingleton{privatestaticSingletonsSingleton;privateSingleton(){}publicstaticSingletongetInstance(){if(sSingleton==null){sSingleton=newSingleton();//lineA}returnsSingleton;}}上述做法好像沒啥問題,由于mSingleton是靜態(tài)的

3、,因此能夠保證程序運行過程中只存在一個實例。但是針對多線程情況,就可能有問題,比如有2個線程同時并發(fā)調用getInstance方法,并且同時執(zhí)行到了lineA,這個時候還是會各自new一個對象出來,也就是說,存在了兩個實例,這違背了單例模式的概念,下面我們改進一下:publicclassSingleton{privatestaticSingletonsSingleton;privateSingleton(){}publicstaticSingletongetInstance(){synchronized

4、(Singleton.class){if(mSingleton==null){sSingleton=newSingleton();}returnsSingleton;}}}上述做法的確是沒啥問題了,getInstance方法中對Singleton.class加鎖,可以保證同一時刻只有一個線程能夠進入getInstance方法?,F在考慮一種情況,還是我們的比較龐大的工程,在某個變態(tài)的時刻,我們需要訪問Singleton對象100次,注意是高并發(fā)下的同時訪問,會是什么情形呢?大概是這樣的:100個線程進入g

5、etInstance方法以后開始搶mSingleton的所有權,這個時候,有一個線程獲得了鎖,然后順利地得到了Singleton實例,接著會是什么情形呢?應該是這樣的:剩下99個線程開始搶mSingleton的所有權,一直這樣類推下去,可能有一個線程運氣比較差,搶了100次才搶到鎖,程序的表現可能是這樣的:這個運氣差的線程被阻塞在getInstance方法中,遲遲無法返回,如果需要返回數據給ui的話,那么ui將遲遲不會得到更新。我們需要看一下上述代碼,真的需要每次進入getInstance方法都要獲得鎖

6、嗎?其實不是的,整個Singleton類中,對mSingleton進行訪問的地方分為兩類:讀和寫,而且僅當mSingleton為null的時候才會寫,mSingleton一旦創(chuàng)建完畢,后面就只剩下讀操作了,再怎么高并發(fā)也沒什么關系了,反正mSingleton已經是現成的,直接讀就可以了,看如下采用double-check機制的改進代碼:publicclassSingleton{privatevolatilestaticSingletonsSingleton;privateSingleton(){}pub

7、licstaticSingletongetInstance(){if(sSingleton==null){//lineAsynchronized(Singleton.class){//lineCif(sSingleton==null)sSingleton=newSingleton();//lineB}}returnsSingleton;}}上述代碼近乎完美,可以滿足幾乎所有場合(采用反射和類加載器另當別論)。上述代碼的好處在于:第一次創(chuàng)建實例的時候會同步所有線程,以后有線程再想獲取Singleton的實

8、例就不需要進行同步,直接返回實例即可。還有double-check的意義在于:假設現在有2個線程A和B同時進入了getInstance方法,線程A執(zhí)行到lineA行,線程B執(zhí)行到lineB行,由于B線程還沒有初始化完畢,sSingleton還是null,于是線程A通過了sSingleton==null的判斷,并且往下執(zhí)行,碰巧,當線程A執(zhí)行到lineC的時候,線程B初始化完畢了,然后線程B返回,注意,如果沒有double-check,這個時

當前文檔最多預覽五頁,下載文檔查看全文

此文檔下載收益歸作者所有

當前文檔最多預覽五頁,下載文檔查看全文
溫馨提示:
1. 部分包含數學公式或PPT動畫的文件,查看預覽時可能會顯示錯亂或異常,文件下載后無此問題,請放心下載。
2. 本文檔由用戶上傳,版權歸屬用戶,天天文庫負責整理代發(fā)布。如果您對本文檔版權有爭議請及時聯系客服。
3. 下載前請仔細閱讀文檔內容,確認文檔內容符合您的需求后進行下載,若出現內容與標題不符可向本站投訴處理。
4. 下載文檔時可能由于網絡波動等原因無法下載或下載錯誤,付費完成后未能成功下載的用戶請聯系客服處理。