我想从主线程中调用一个对象
MyObj* backgroundObject = [[MyObj alloc] initInBackground];
BOOL result = [backgroundObject computeResult];
但是让backgroundObject的所有方法都在另一个线程中计算。
并且还有backgroundObj能够向其委托发送消息。我该怎么办?有可能吗?
答案 0 :(得分:7)
正如其他人所指出的那样,任何一个线程都不存在NSObject,当你开始执行它的方法时,一个线程才会起作用。
我的建议是每次在对象上调用方法时都不使用手动线程,而是使用NSOperations和NSOperationQueue。将NSOperationQueue作为对象的实例变量,并调用对象上的各种方法创建插入队列的NSOperations。 NSOperationQueue将在后台线程上处理这些操作,避免了对多次访问方法所需的所有手动线程管理。
如果你使这个NSOperationQueue的最大并发数为1,你还可以避免在后台线程上执行的各种操作之间锁定对象内的共享资源(当然你仍然需要锁定实例变量可以从外部世界访问。)
对于委托或其他对象的回调,我建议使用-performSelectorOnMainThread:withObject:waitUntilDone
,这样您就不必考虑使这些委托方法成为线程安全的。
有关详情,请参阅Concurrency Programming Guide。
答案 1 :(得分:6)
当然,您可以使用NSThread
,backgroundObject
使用performSelectorOnMainThread:
与代表联系。
答案 2 :(得分:2)
线程AFAIK中不存在对象。您发送给对象的函数将始终在您发送给它的线程上执行(除非您使用NSThread或performSelectorOnMainThread或其他内容)。
答案 3 :(得分:1)
您需要的是NSOperation和block / delegate参数,以通知调用者完成。
查看NSOperation和NSOperationQueues
的文档答案 4 :(得分:0)
您应该使用GCD:
/*
* I didn't initalised your object in background, because
* because in the most cases you need your object to stick around
* and only perfom the time consimung calculations in background
*/
MyObj* backgroundObject = [[MyObj alloc] initInBackground];
...
- (void)startBackgroundTask {
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
//in a perfectly async non blocking block :-)
BOOL result = [backgroundObject computeResult];
dispatch_async(dispatch_get_main_queue(), ^{
//post your result, or do something else with your result
[[NSNotificationCenter defaultCenter] postNotificationName:"backgroundComputeResultDone" object:[NSNumber numberWithBool:result]];
if (result) {
//do some stuff
}
});
});
}
也许您可以查看来自apple here的这两个视频: