1

我已经注册了一个 NSTask 对象的 NSTaskDidTerminateNotification。一切正常,但任务需要时间才能启动,所以我将启动移至后台(使用 performSelectorInBackground)。

  • 通知中心的注册和任务本身的创建发生在主线程上
  • 几秒钟后,任务在后台启动
  • 通知不再到达:(

有没有办法我可以以某种方式调整通知的代码以再次工作?

4

2 回答 2

1

首先NSTask 不是线程安全的。从单独的线程中使用它的实例或完全避免它时,您需要小心。

其次,据我所知,NSNotifications 仅在发布通知的线程上传递。通知由 NSTask 对象本身发布,该对象显然在辅助线程上终止,但您已在主线程上注册通知。有关更多信息,请参阅文档

你能简单地处理后台线程上的整个任务和通知序列吗?

于 2013-11-05T03:08:28.083 回答
1

NSTask注册一个私有运行循环源来监视它启动的线程的运行循环中的任务。如果该线程不再继续存在并运行它的运行循环,那么 Cocoa 就不会注意到任务已经终止。如果 Cocoa 没有注意到它,那么它就无法将通知发布给您的观察者。

如果您正在做的唯一事情-performSelectorInBackground:...是调用-launch任务的方法,那么线程不会留下来也不会运行它的运行循环。(同样,不能依赖服务于 GCD 队列的工作线程来保持现有或运行它们的运行循环。)您可以在后台调用更复杂的方法来启动任务然后运行运行循环,但这应该没必要。

您确定启动任务需要花费大量时间吗?真的不应该。 NSTask旨在使任务可以在主线程上创建、启动和监视而不会使其无响应。

于 2013-11-05T07:10:50.177 回答