在 OS X 10.5+ 环境中编写相当典型的 Mac 代码时,使用垃圾收集有哪些缺点?
到目前为止,我编写的所有其他内容要么与 10.4 兼容,要么在 iPhone 上,所以我对保留/发布已经相当满意,但现在我正在处理一个只有 10.5 的更大项目,我想知道是否有继续使用 Objective-C 2.0 垃圾收集器有什么缺点吗?
你们有什么感想?
在 OS X 10.5+ 环境中编写相当典型的 Mac 代码时,使用垃圾收集有哪些缺点?
到目前为止,我编写的所有其他内容要么与 10.4 兼容,要么在 iPhone 上,所以我对保留/发布已经相当满意,但现在我正在处理一个只有 10.5 的更大项目,我想知道是否有继续使用 Objective-C 2.0 垃圾收集器有什么缺点吗?
你们有什么感想?
如果您正在编写新的 Cocoa 代码并针对 Mac OS X 10.5,请使用 Objective-C 垃圾回收。
如果您正在编写一些可能还需要在 iPhone 上运行的代码,您可以非常轻松地为这两个模型编写和测试该代码,方法是将该代码保存在一个单独的框架中,使用属性-retain
和-release
用途编写它,并设置您的框架和您的单元测试目标为GC-supported而不是GC-only。
Xcode 将运行你的单元测试包两次,一次开启 GC,一次关闭 GC,你的框架将在两种执行模型下都可用。然后,如果您最终想要将该模型级代码带到 iPhone 中,您可以将其放入一个针对 iPhone 的静态库中,或者将其直接包含在您的 iPhone 项目中。
不过,无论您是否考虑在 iPhone 上运行代码,如果您的应用程序需要 Leopard,则绝对应该以垃圾收集为目标。它将简化开发并且Objective-C 垃圾收集器执行得非常好。
如果有可能将您的应用程序移植到 iPhone,您不应该使用它。
如果您有特殊用例,垃圾收集可能会对性能产生不利影响。没有 GC,您可以精确控制对象的销毁,而 GC 世界则不是这样。在大多数项目中,打开 GC 是值得的,因为它不易出错且更容易。
理论上,没有 GC 的内存管理总是比使用 GC 更快,但是,在大多数实际应用中并非如此(因为 GC 通常比人类更优化)。
我更喜欢自己处理内存管理,仅仅是因为我喜欢拥有那种级别的控制权。我从其他语言 (C#) 的经验中知道,GC 不允许您完全忽略内存问题,这在 Cocoa 中也是一样的,例如弱引用和使用 (void *) 的回调,其中对象没有被明确拥有由另一个对象。您基本上是在用一组挑战(内存泄漏)换取另一组挑战。就我个人而言,这些天我不会犯太多的内存管理错误,而且我所犯的错误很容易追踪。
在某些情况下(例如为 NSOutlineView 实现数据源方法,您不想保留提供给大纲视图的对象)我认为 GC 会非常有用,但我没有做任何真正的测试呢。
Apple 在GC 编程指南中列出了其他一些优点和缺点。
从 10.8 开始不推荐使用 GC。实际上,采用这项技术从来都不是一个好主意,除了啦啦队,因为性能和稳定性目标从未达到。
“手动”管理内存实际上非常简单,因为管理代码可以在很大程度上被分解出来。我的代码库中与内存管理相关的代码少于 1%,这比它需要的要大。所以我也对 ARC 持怀疑态度,因为它所解决的问题是如此之小,以至于即使是相当小的技术陷阱也让它变得不值得。