《Effective Objective-C 2.0 编写高质量iOS与OS X代码的52个有效方法》(第五十二条:别忘了NSTimer会保留其目标对象)笔记
要点如下:
1、计时器只有放在运行循环中,才能正常触发任务
2、创建计时器:
+ (NSTimer *)scheduledTimerWithTimeInterval:
(NSTimerInterval)seconds //时间间隔
target:(id)target //NSTimer会保留target
selector: (SEL)selector //回调方法
userInfo: (id)userInfo //回调selector时所带的参数
repeats: (BOOL)repeats; //是否反复执行。为NO只执行一次且计时器自动停止,为YES需要手动调用invalidate停止
由于NSTimer会保留target,所以会导致”保留环“,因为target一般是self,而创建的定时器一般会被self所保留(作为self的属性)
3、用block解决”保留环“问题:
首先给NSTimer添加分类EOCBlocksSupport。
NSTimer+EOCBlocksSupport.h
+ (NSTimer *)eoc_scheduledTimerWithTimeInterval: (NSTimeInterval)interval block:(void (^) ())block repeats:(BOOL)repeats;
NSTimer+EOCBlocksSupport.m
+ (NSTimer *)eoc_scheduledTimerWithTimeInterval: (NSTimeInterval)interval block:(void (^) ())block repeats:(BOOL)repeats{
return [self scheduledTimerWithTimeInterval:interval
target:self
selector:@selector(eoc_blockInvoke:)
userinfo:[block copy]
repeats:repeats
];
}
+ (void)eoc_blockInvoke:(NSTimer *)timer{
void (^block)() = timer.userinfo;
if(block){
block();
}
}
创建NSTimer:
#import "NSTimer+EOCBlocksSupport.h"
...
- (void)createTimer{
__weak typeof(self) weakSelf = self;
self.timer = [NSTimer eoc_scheduledTimerWithTimeInterval:5.0f
block: ^{
[weakSelf doSomething];
}
repeats: YES];
}
注:对block的理解,可参考:https://blog.youkuaiyun.com/u012773581/article/details/87795894