6

我有一个后台线程正在做一堆工作 - 加载应用程序。主线程在 UIProgressView 上显示进度。

后台线程是用 performSelectorInBackground 产生的(不过,如果不同的方法使这个问题更容易解决,我不喜欢这种方法)

[self performSelectorInBackground:@selector(loadAppInBackground) withObject:self];

在某些情况下,一个错误导致后台线程崩溃(随着应用程序的发展出现不同的错误),导致进度条停止,但用户没有得到任何错误的明确指示。

我想检测这种情况并且比简单地挂起直到用户放弃等待更优雅地失败。

因为加载过程的持续时间可能会有很大差异,所以简单地超时并不是一个理想的选择。

前台线程检测后台线程失败的最佳方法是什么?由于前台线程忙于处理 UI,是否需要第二个后台线程来监视第一个?这看起来很难看。

是否有一些线程间通信机制可用于“ping”后台进程?更好的是,检查其他线程状态的低级系统机制?

调试器知道所有正在运行的线程......并且似乎知道它们的状态。我想知道我的应用程序是否可以调用来做同样的事情。

4

3 回答 3

1

一种常见的技术是有一个额外的线程来检查相关线程的生命迹象——所谓的心跳线程。心跳线程通过检查它是否及时响应来轮询线程,如果没有,则认为线程死亡并终止它。

一个简单的心跳线程实现是检查一个由另一个线程定期递增的计数器,如果计数器在一定时间内没有递增,则认为它已死,然后可以采取适当的措施,例如重新启动线程或杀死应用程序。另一种更常见的方式是如果 hb 线程向线程发送消息并检查是否有超时响应。

于 2012-10-24T04:32:57.313 回答
1

如果后台任务以某种规则循环运行(例如,有一个大循环在其中完成了大部分工作),它可以不时设置一个标志以指示它仍然存在。

一种方法是在[NSDate timeIntervalSinceReferenceDate]某处存储后台线程,并且在您的主线程中,偶尔(可能在计时器上)将其与当前时间进行比较。如果差异大于某个合理的限制,您可以猜测后台线程已经死亡。

另一种方法是让后台线程简单地设置一个布尔值,并让主线程询问它并定期清除它。如果布尔值在主线程询问之间没有再次设置,您可以推断它已经死亡。

第一种技术的优点是您可以“调整”“合理限制”以容忍在时间上有些不规则的代码(在任一线程中)。第二种方法通常需要更可预测的时间安排。

当然,无论哪种方法,如果后台线程刚刚结束而您还没有意识到这一点,您都希望以某种方式避免“吹哨”。

于 2012-10-24T01:37:06.933 回答
0

目标 c 中似乎没有直接检查后台线程状态的机制。提供的任何答案都是不错的选择……要么超时,要么让线程创建某种证明其继续存在的证据。

我希望有一些更简单、可靠和实时的东西。

我将尝试在线程中捕获异常,并可能会产生诸如“BackgroundThreadException”之类的通知,前台线程可以侦听并做出反应。

于 2015-08-11T21:11:58.933 回答