自动释放:当您使用NARC时始终使用?

时间:2010-05-26 09:33:44

标签: iphone memory-management

我知道这个问题看起来像是一个骗局:我检查过它不是

在谈论NARC时,the author of this blog says,“就个人而言,我喜欢立即自动发布任何我在同一行上发布的内容。”这与我在Apple网站和书籍中看到的所有示例完全相反,其中仅在必须返回对象且无法立即释放时才使用自动释放。一般来说,这个想法是autorelease是内存密集型的,可能会破坏你的程序(虽然它使代码更清晰)。从 Appress开始iPhone 3开发

  

这些物品可能会有害   对应用程序内存的影响   脚印。可以使用   自动释放,但只尝试使用它   当你真的需要时,而不仅仅是   保存键入一行或两行代码。

我不是在问自动释放是否比明确调用release(它是)更糟糕,而是:

在iPhone的大多数“正常”情况下,用较早的自动释放替换后来的版本有多么糟糕(使用相同的方法)?此外,在什么情况下绝对禁止这样做?


我的猜测是,与使用垃圾收集器(因为MonoTouch应用程序成功完成)相比,自动释放几乎不会影响您的内存占用,并且Vincent的建议正确,并且可以使代码更清晰,更少意外的内存泄漏

2 个答案:

答案 0 :(得分:3)

使用自动释放没有任何问题,但是当你在循环中分配对象时,你应该总是明确地调用release。

使用自动释放:

for (int i=0;i<1000;i++) {
    NSString *s = [[[NSString alloc] init] autorelease];
}

// at this point, there are 1,000 unreleased string objects in memory

使用发布:

for (int i=0;i<1000;i++) {
    NSString *s = [[NSString alloc] init];

    [s release];
}

// at this point, no string objects are "alive"

正如您所看到的,在循环中使用自动释放时必须非常小心。

答案 1 :(得分:2)

你应该知道自动释放是如何工作的。应用程序中的每个线程通常都有一个自动释放池。对象可以在池中注册。在注册时,池确定它们所属的堆栈帧,并且只要剩下该堆栈帧,它就会自动从池中弹出。

虽然这可能看起来很昂贵(而且它肯定与直接保留/释放相比),但我认为它甚至不接近代码标记和扫描垃圾收集器可以拥有的成本。

自动释放确实闪耀的地方是在所有可能引发异常并且没有尝试/捕获的情况下。在这种情况下,自动释放肯定比直接释放更好。

但是,有些情况下你应该避免自动释放(对于你应该试图避免这些情况的garabge收集环境也是如此)。在一个运行了很多次的循环中创建临时的,自动释放的对象就是这种情况,这给垃圾收集器或自动释放池带来了很大的压力。

在工作线程中应该避免使用autorelease替换发行版,这些线程非常简单并且可以在没有自动释放池的开销的情况下生存。因此,指南是:每当你不确定自动释放时,你应该避免它。