【问题标题】:How can I make sure NSOperations execute in a failsafe way?如何确保 NSOperations 以故障安全的方式执行?
【发布时间】:2010-08-04 10:52:24
【问题描述】:

我想要什么

我的应用程序中有一个 NSOperationQueue,在应用程序退出之前处理所有操作至关重要。我在退出时有以下代码,以确保 NSOperationQueue 在退出前为空:

if ([NSThread isMainThread]) {
    while ([[operationQueue operations] count] > 0) {
        [[NSRunLoop currentRunLoop] runUntilDate:[NSDate dateWithTimeIntervalSinceNow:0.05]];
    }
} else {
    [operationQueue waitUntilAllOperationsAreFinished];
}

在 NSOperation 在完成之前“冻结”并阻塞整个队列之前,我遇到了我的代码问题。显然,在这种情况下,我的代码应该抛出一个异常,现在它会抛出异常。

但我仍然想防止在操作停止并阻塞队列时发生任何奇怪的事情,从而导致应用程序永远不会退出并且错误不会被捕获。

我的垃圾解决方案

我正在考虑在队列完成其操作时设置一个超时。然后当它超时时,我可以抛出一个异常,然后问题就会被捕获。

但是,这感觉不对。理想情况下,我不想依赖计时器来确保工作完成。

我的问题

有没有更好的、故障安全的方法来确保我的操作没有冻结?

【问题讨论】:

  • 您的操作是通过什么方式“冻结”的?

标签: cocoa timeout nsoperation nsoperationqueue


【解决方案1】:

如果我明白...

  • 您想知道您的运营没有冻结...变成...
  • 您想知道您的所有操作都将完成执行...变成...
  • 你要解决the halting problem

祝你好运。

不过,实际上,您使用waitUntilAllOperationsAreFinished 所做的事情与您将获得的一样好。您可以添加另一个类来监视每个操作并确保它不会运行太久(比您预期的运行时间长 10 倍),此时它将 -cancel NSOperation (或多或少你的计时器方法)。但是,即使这样也不是万无一失的,因为操作可能会在您无法检查 -isCancelled 的情况下被阻止(例如,在系统调用中)。

【讨论】:

  • 感谢您的出色回答,戴夫。很高兴可以放心,我的超时方法不会离基地太远。我满足于因操作队列超时而崩溃,那么至少我知道这里存在某种问题。
  • 嗯,停止问题的意思是:“我们能否构建一个算法来确定任何算法是否会在某个时间点停止。”据我了解,OP 不会采用那种广泛的方法:)
【解决方案2】:

正如 radiospiel 在上面的 cmets 中所说,您实际上并不是在寻找停机问题。如果您可以对操作的长度进行良好的上限和下限,您可以为每个操作设置一个时间窗口,看看它们是否已经完成。如果你不能做好下限,那么这将变得低效。此外,如果您的任何操作具有无限循环,它们仍然可能使其他线程饿死,具体取决于您所处的环境。(然后您就不走运了。)

使用过于宽泛的问题概括将其称为停机问题是计算机科学的经典错误之一。您并不总是需要一般问题。见:http://valgrind.org/

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-10-20
    • 1970-01-01
    • 2016-02-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多