關於GCD中單例的實現,不僅僅是 dispatch_once(視圖完整版)


之前太過於年輕,總結的簡單單例模式傳送門: http://www.cnblogs.com/PSSSCode/p/5482419.html

這篇博客主要講的是GCD中的單例模式,大家肯定會想到dispatch_once這個函數,但是這篇博客不僅僅是dispatch_once的使用。

1、單例模式簡介(面試常考的。。。)

  • 單例模式的作用
    • 可以保證在程序運行過程,一個類只有一個實例,而且該實例易於供外界訪問
    • 從而方便地控制了實例個數,並節約系統資源
  • 單例模式的使用場合  
    • 系統  
      • UIApplication、NSUserDefaults、NSFileManager、NSNoticationCenter 
    • 自定義
      • 在某個應用程序中,共享一份資源(這份資源只需要創建初始化一次)
      • 網絡計數器
      • 分享界面、登錄界面、評論界面不登錄會跳轉到唯一界面登錄界面(單例實現)
      • 點擊跳轉,控制器設置為單例,該控制器不會被銷毀,依然存在內存中,返回再次回去,再點擊進來,則會快速進入不會創建對應的新的控制器

2、具體代碼

  • 只需實現三個方法
    • 1、allocWithZone:       (alloc底層調用該方法)
    • 2、shareCar          (一種命名規范)
    • 3、copyWithZone      (對應實例變量 調用copy會調用該方法)

默認情況

添加單例情況

 1 @interface PSSCar() // <NSCopying>
 2 
 3 @end
 4 
 5 @implementation PSSCar
 6 
 7 static PSSCar *_car;
 8 
 9 + (instancetype)allocWithZone:(struct _NSZone *)zone
10 {
11     static dispatch_once_t onceToken;
12     dispatch_once(&onceToken, ^{
13         _car = [super allocWithZone:zone];
14     });
15     return _car;
16 }
17 
18 + (instancetype)sharedCar
19 {
20     static dispatch_once_t onceToken;
21     dispatch_once(&onceToken, ^{
22         _car = [[self alloc] init];
23     });
24     return _car;
25 }
26 
27 - (id)copyWithZone:(NSZone *)zone
28 {
29     return _car;
30 }

 

3、封裝代碼

當一個項目中多個類需要使用單例,則需要在對應類的.m文件中寫以上的代碼,並且代碼幾乎沒有差別,所有可以將上面的代碼封裝成一個工具類,並在工具類中使用宏定義,減少代碼冗余。

// .h文件
#define PSSSingletonH(name) + (instancetype)shared##name;

// .m文件
#define PSSSingletonM(name) \
static id _instance; \
 \
+ (instancetype)allocWithZone:(struct _NSZone *)zone \
{ \
    static dispatch_once_t onceToken; \
    dispatch_once(&onceToken, ^{ \
        _instance = [super allocWithZone:zone]; \
    }); \
    return _instance; \
} \
 \
+ (instancetype)shared##name \
{ \
    static dispatch_once_t onceToken; \
    dispatch_once(&onceToken, ^{ \
        _instance = [[self alloc] init]; \
    }); \
    return _instance; \
} \
 \
- (id)copyWithZone:(NSZone *)zone \
{ \
    return _instance; \
}

 

在對應類的.h和.m中只需要調用宏定義重新命名的響應方法即可,同時將本類的類名傳入,即可實現快速單例模式的實現與使用

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM