標籤:
理解
- 變數
- 範圍
- 變數廢棄
- 持有對象
- 釋放對象
- 對象所有者(引用計數)
- 對象廢棄
- 變數所有權修飾符對對象的影響
對象相互持有導致迴圈強引用,舉例如反覆執行任務的NSTimer對象的目標對象
又保留了計時器對象,若該NSTimer對象被目標對象持有,便必定會發生迴圈強引用,因為NSTimer對象會持有目標,
而該NSTimer對象又是目標對象的成員變數也就是目標對象又持有該NSTimer對象
此迴圈強引用會一直持續到目標對象調用NSTimer對象的invalidate方法釋放該NSTimer對象
可通過擴充NSTimer類利用block與__weak所有權修飾符解決該迴圈強引用
#import<Foundation/Foundation.h>@interface NSTimer(BlocksSupport)+(NSTimer *)scheduledTimerWithTimeInterval:(NSTimeInterval)intervalblock:(void(^)())blockrepeats:(BOOL)repeats;@end@implementation NSTimer(BlockSupport)+(NSTimer *)scheduledTimerWithTimeInterval:(NSTimeInterval)intervalblock:(void(^)())blockrepeats:(BOOL)repeats{return [self scheduledTimerWithTimeInterval:intervaltarget:selfselector:@selector(blockInvoke:)userInfo:[block copy]repeats:repeats];}+(void)blockInvoke:(NSTimer *)timer{void(^block)()=timer.userInfo;if(block){block();}}
//在別的Class類使用的時候-(void)startAction{__weak Class *weakSelf=self;//定義一個指向自己的弱引用_myTimer=[NSTimer scheduledTimerWithInterval:5.0 block:^{Class *strongSelf=weakSelf;/*塊捕獲該指向自己的弱引用,不直接捕獲普通的self變數,因此block不持有該Class對象然後馬上讓__strong變數持有該__weak的Class對象保證執行個體在執行期間持續存活,也就是說strongSelf也是持有了Class對象的,但是,但是,但是,strongSelf是在block體中聲明的變數,其生命週期僅存block塊,在block塊執行完後便釋放,也就不持有Class對象了*/[strongSelf excueAction]; } repeats:YES];}-dealloc{[_myTimer invalidate];/*當外界持有Class對象的最後一個引用將其釋放的時候,該方法會被執行,從而還會讓計時器停止工作。若開發人員忘記在dealloc中調用invalidate方法停止計時器,那麼計時器執行的block塊中的weakSelf會變成nilstrongSelf也就指向了nil,從而計時器執行空操作。*/}
Objective-C 記憶體管理淺析與迴圈強引用舉例