【发布时间】:2013-02-15 00:15:03
【问题描述】:
我正在使用如下的 NSThread
NSThread * thread = [[NSThread alloc] initWithTarget:object selector:@selector(bg) object:nil];
[thread start];
稍后我想停止线程并释放对象,如下所示:
[thread cancel];
[object release];
这似乎工作正常。但是,当我查看泄漏工具时,我看到一些神秘的泄漏不是来自我的代码的任何地方(一个空的 NSArray)。当我查看 malloc 历史记录时,我看到 NSArray 是在“willChangeValueForKey”方法中分配的,该方法最终从我的 [object dealloc] 调用。它恰好将委托设置为零。该委托正在被观察(因此 willChangeValueForKey?)。 [object dealloc] 从 [NSThread exit] 调用。
我的猜测是,这是因为 [线程取消] 不会立即停止线程(毕竟它在不同的线程中)。然后我们在主线程上释放对象。 这使得它的 retainCount 为 1。然后 NSThread 将在它真正减速时释放对象。看来这会导致泄漏。我尝试了这个快速更改来验证我的假设:
[thread cancel];
[NSThread sleepForTimeInterval:1];
// This makes it wait until the thread releases [object]
[object release];
问题:为什么让 NSThread 释放我的对象是不安全的?是否与dealloc中的观察者代码不安全有关?
【问题讨论】:
-
您的
willChange/didChange是否发生在addObserver:和removeObserver:被调用的同一线程上? -
你的线程有自己的自动释放池吗?
-
自动释放池:是的。至于 iluvcapra 的问题:我不确定。这段特殊的代码非常复杂,所以我不能 100% 确定。将它们放在不同的线程上会导致泄漏吗?
-
您可以想象一场比赛,其中一个线程正在执行观察例程,而另一个线程正在将其作为观察者移除。
标签: objective-c cocoa nsthread