我有一个很奇怪的问题。为了使短,我会写一些伪代码:为什么我会在NSTimer选择器中获得EXC_BAD_ACCESS?
init: create a dictionary and insert n elements.
create a "repeat timer" and add it to the currentRunLoop using the timerRefresh selector.
timerRefresh: using a list of keys, find the items in the dictionary
if the item exists -> call a function
所以,对于一个未知的原因,我得到一个EXC_BAD_ACCESS,当我做:
[item function];
但我跟踪我的地址从字典项目,这是可以的。字典中项目的引用计数仍为1.不会调用字典中项目的{release,dealloc}。一切似乎都很好。另外,为了让它变得更糟,它适用于某些项目。
所以,我想知道是否有线程问题?或别的什么隐晦?
调用堆栈是相当简单:
#0 0x93e0604b in objc_msgSend_fpret
#1 0x00f3e6b0 in ??
#2 0x0001cfca in -[myObject timerRefresh:] at myObject.m:000
#3 0x305355cd in __NSFireTimer
#4 0x302454a0 in CFRunLoopRunSpecific
#5 0x30244628 in CFRunLoopRunInMode
#6 0x32044c31 in GSEventRunModal
#7 0x32044cf6 in GSEventRun
#8 0x309021ee in UIApplicationMain
#9 0x000027e0 in main at main.m:14
因此,任何建议在哪里看,将不胜感激。
---编辑#1 ---
@Laurent:这是我的改写实际值符合我的例子一个错字。 (固定)
@Jeremy:我会尝试发布一些代码来帮助。代码已被简化。
定时器初始化+刷新功能:
_refreshTimer = [[NSTimer alloc] initWithFireDate:[NSDate dateWithTimeIntervalSinceNow:5] interval:5
target:self selector:@selector(onTimerRefresh:) userInfo:nil repeats:YES];
[[NSRunLoop currentRunLoop] addTimer:_refreshTimer forMode:NSDefaultRunLoopMode];
//...
(void)onTimerRefresh:(NSTimer*)theTimer {
// the actual code is here. I will rewrite it so it's simpler:
for (MyKey key in keys) {
MyObject* object = [dictionary objectForKey:key];
if (object)
[object function];
}
}
我希望这是一点点清晰。
对,我在我的“功能”中评论了一切,看起来好像不会崩溃。我会让它运行多一点,但我没有做任何特殊的功能(内存相关)。只需更新一些枚举值。
---编辑#2 ---
@Laurent:你说得对callstak,我犯了一个巨大的错误。它应该是计时器方法而不是函数。我只是修复它。对不起,这个错误。但FYI,方法签名是:
- (bool)update;
对“function”方法的调用和存在“functionm:”的堆栈跟踪之间存在不匹配。可以吗? 你也可以发布一些相关的代码? – 2010-05-27 14:17:39
@Laurent +大约一百万用于“发布一些相关的代码” – JeremyP 2010-05-27 14:44:15
@AngeDeLaMort:一些问题:你是什么意思的“timerRefresh”选择器? NSTimer上没有这样的选择器。你的堆栈跟踪中没有timerRefresh。你从哪里得到钥匙清单?请在运行循环中发布定时器初始化和调度的代码,以及定时器触发时会发生什么。 – JeremyP 2010-05-27 14:56:25