創建單例的2種方法

創建一個單例很多辦法。我先列舉一個蘋果官方文檔中的寫法。

[cpp]view plaincopy

staticAccountManager?*DefaultManager?=?nil;

+?(AccountManager?*)defaultManager?{

if(!DefaultManager)?DefaultManager?=?[[self?allocWithZone:NULL]?init];

returnDefaultManager;

}

當然,在iOS4之后有了另外一種寫法:

[cpp]view plaincopy

+?(AccountManager?*)sharedManager

{

staticAccountManager?*sharedAccountManagerInstance?=?nil;

staticdispatch_once_t?predicate;

dispatch_once(&predicate,?^{

sharedAccountManagerInstance?=?[[self?alloc]?init];

});

returnsharedAccountManagerInstance;

}

該寫法來自objcolumnist,文中提到,該寫法具有以下幾個特性:

1. 線程安全。

2. 滿足靜態分析器的要求。

3. 兼容了ARC

然后我還有點好奇的是dispatch_once,這個函數,沒見過啊。

于是就到官方的文檔里找找看,是怎么說的。

下面是官方文檔介紹:

dispatch_once

Executes a block object once and only once for the lifetime of an application.

void dispatch_once(

dispatch_once_t *predicate,

dispatch_block_t block);

Parameters

predicate

A pointer to adispatch_once_tstructure that is used to test whether the block has completed or not.

block

The block object to execute once.

Discussion

This function is useful for initialization of global data (singletons) in an application. Always call this function before using or testing any variables that are initialized by the block.

If called simultaneously from multiple threads, this function waits synchronously until the block has completed.

The predicate must point to a variable stored in global or static scope. The result of using a predicate with automatic or dynamic storage is undefined.

Availability

Available in iOS 4.0 and later.

Declared In

dispatch/once.h

我們看到,該方法的作用就是執行且在整個程序的聲明周期中,僅執行一次某一個block對象。簡直就是為單例而生的嘛。而且,有些我們需要在程序開頭初始化的動作,如果為了保證其,僅執行一次,也可以放到這個dispatch_once來執行。

然后我們看到它需要一個斷言來確定這個代碼塊是否執行,這個斷言的指針要保存起來,相對于第一種方法而言,還需要多保存一個指針。

方法簡介中就說的很清楚了:對于在應用中創建一個初始化一個全局的數據對象(單例模式),這個函數很有用。

如果同時在多線程中調用它,這個函數將等待同步等待,直至該block調用結束。

這個斷言的指針必須要全局化的保存,或者放在靜態區內。使用存放在自動分配區域或者動態區域的斷言,dispatch_once執行的結果是不可預知的。

總結:1.這個方法可以在創建單例或者某些初始化動作時使用,以保證其唯一性。2.該方法是線程安全的,所以請放心大膽的在子線程中使用。(前提是你的dispatch_once_t *predicate對象必須是全局或者靜態對象。這一點很重要,如果不能保證這一點,也就不能保證該方法只會被執行一次。)

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容

  • 創建一個單例很多辦法。我先列舉一個蘋果官方文檔中的寫法。 [cpp]view plaincopy staticAc...
    乖乖圣斗士閱讀 256評論 0 0
  • GCD是異步執行任務的技術支之一,開發者只需要將想要執行的block任務添加到適當的Dispatch Queue(...
    zziazm閱讀 1,773評論 0 8
  • NSThread 第一種:通過NSThread的對象方法 NSThread *thread = [[NSThrea...
    攻城獅GG閱讀 853評論 0 3
  • 目錄 dispatch_once dispatch_once低負載特性 備注 參考文章 相信大家對dispatch...
    時間在改變閱讀 1,668評論 0 6
  • 官方文檔中的寫法: iOS4之后有了另外一種寫法: 該寫法來自 objcolumnist,文中提到,該寫法具有以下...
    AlexLi_閱讀 180評論 0 0