如何使用NSTimers作为关联引用?

时间:2012-01-20 20:34:38

标签: objective-c

我尝试了以下内容:

- (void)setupTimer {    
NSTimer *timer = [NSTimer scheduledTimerWithTimeInterval:2.0 target:self selector:@selector(doSomething) userInfo:nil repeats:YES];
    objc_setAssociatedObject(self, &key, timer, OBJC_ASSOCIATION_RETAIN);
    [timer invalidate];
}

- (void)doSomething { /* ... */ }
- (void)afterDoingSomething { [objc_getAssociatedObject(self, &key) invalidate]; }

然而,由于某种原因,计时器没有打勾(我没想到它会这样做;这段代码对我来说不太合适)。有没有办法让它......工作?

3 个答案:

答案 0 :(得分:5)

您在创建和安排计时器后立即使计时器失效。移除[timer invalidate];中的-setupTimer行:

- (void)setupTimer {    
    NSTimer *timer = [NSTimer scheduledTimerWithTimeInterval:2.0 target:self selector:@selector(doSomething) userInfo:nil repeats:YES];
    objc_setAssociatedObject(self, &key, timer, OBJC_ASSOCIATION_RETAIN);
}

来自documentation

  

[invalidate]停止接收器再次发射并请求   它从运行循环中删除。

假设此代码属于某个类别,我是否正确?否则,我想不出一个很好的理由让计时器成为一个关联的对象,而不是只使用常规的实例变量。

答案 1 :(得分:1)

您必须误解invalidaterelease。 当你设置下一个项目时,objc_setAssociatedObject为你做release

答案 2 :(得分:0)

我不认为将计时器设置为关联参考是个问题。

  1. 您在计时器实际启动之前就已经杀了它(invalidate这样做了。)

  2. 您的- (void)doSomething方法应具有不同的签名:- (void)doSomething: (NSTimer*)theTimer

  3. 您可能正在泄露记忆,您应该在objc_setAssociatedObject(self, &key, nil, OBJC_ASSOCIATION_RETAIN);afterDoingSomething