在Objective-C中使用异常的成本是多少?

Lot*_*har 9 error-handling performance cocoa exception objective-c

我的意思是在clang或gcc版本的当前实现中.

C++和Java人总是告诉我,除非抛出异常,否则异常不会花费任何性能.Objective-C也是如此吗?

jus*_*tin 9

C++和Java人总是告诉我,除非抛出异常,否则异常不会花费任何性能.Objective-C也是如此吗?

简答

仅适用于64位OS X和iOS.

他们并非完全免费.更准确地说,该模型经过优化,可以在常规执行期间最大限度地降低成本(在其他地方产生影

详细解答

在32位OS X和iOS上,异常具有运行时成本,即使它们没有被抛出.这些体系结构不使用零成本例外.

在64位OS X中,ObjC转而借用C++的"Zero Cost Exceptions".零成本异常具有非常低的执行开销,除非抛出.零成本例外有效地将执行成本转移到二进制大小.这是他们最初未在iOS中使用的主要原因之一.启用C++异常和RTTI可以将二进制大小增加50%以上 - 当然,我认为纯粹的ObjC中这些数字要低得多,因为在展开时执行的数量较少.

在arm64中,异常模型从Set Jump Long Jump更改为Itanium派生的Zero Cost Exceptions(根据程序集判断).

但是,Idiomatic ObjC程序没有编写或准备从异常中恢复,因此您应该保留它们用于您不打算从中恢复的情况(如果您决定使用它们).有关ARCClang手册以及引用页面的其他部分的更多详细信息.

  • 此外,您应该指出异常导致ARC的问题:http://clang.llvm.org/docs/AutomaticReferenceCounting.html - "默认情况下使代码异常安全会对代码造成严重的运行时和代码大小处罚实际上并不关心异常安全.因此,ARC生成的代码默认在异常时泄漏,如果过程将立即终止,那就没问题了." (3认同)

Dan*_*ear 6

根据Mac OS X v10.5中针对Objective-C运行时的2007年发布说明,他们重新编写了Objective-C异常的64位实现,以提供"零成本"尝试块和与C++的互操作性.

显然,这些"零成本"尝试块在进入尝试时不会产生时间损失,这与它必须调用setjmp()和其他函数的32位对应物不同.显然扔掉它们"要贵得多".

这是我在Apple的发行说明中可以找到的唯一信息,所以我不得不假设这仍然适用于今天的运行时,因此,32位异常=昂贵,64位异常="零成本"