是否有必要在 Swift 程序中使用 autoreleasepool? [英] Is it necessary to use autoreleasepool in a Swift program?
问题描述
在 这个 WWDC14 演示文稿的第 17 页上,它说
<块引用>使用Objective-C?仍然需要管理自动释放池
autoreleasepool {/* 代码 */}
这是什么意思?这是否意味着如果我的代码库没有任何 Objective-C 文件,autoreleasepool {}
是不必要的?
在一个相关问题的回答中,有一个例子,其中autoreleasepool
可以有用:
- (void)useALoadOfNumbers {for (int j = 0; j <10000; ++j) {@autoreleasepool {for (int i = 0; i <10000; ++i) {NSNumber *number = [NSNumber numberWithInt:(i+j)];NSLog(@"number = %p", number);}}}}
如果将上面的代码翻译成 Swift 并删除 autoreleasepool
,Swift 是否足够聪明,知道应该在第一个 } 之后释放
(像其他一些语言一样)?number
变量
autoreleasepool
模式在 Swift 中用于返回 autorelease
对象(由您的 Objective-C 创建代码或使用 Cocoa 类).Swift 中的 autorelease
模式与 Objective-C 中的功能非常相似.例如,考虑你的方法的这个 Swift 版本(实例化 NSImage
/UIImage
对象):
func useManyImages() {让文件名 = pathForResourceInBundle对于 _ 在 0 ..<5{自动释放池{对于 _ 在 0 ..<1000 {让图像 = NSImage(contentsOfFile: 文件名)}}}}
如果你在 Instruments 中运行它,你会看到一个带有 5
小山丘的分配图(因为外部 for 循环),如下所示:
但是如果您在没有自动释放池的情况下执行此操作,您会看到峰值内存使用量更高:
autoreleasepool
允许您在 Swift 中明确管理何时释放自动释放对象,就像您在 Objective-C 中一样.
注意:在处理 Swift 原生对象时,您通常不会收到自动释放对象.这就是为什么演示文稿提到了使用 Objective-C"时只需要这个的警告,尽管我希望 Apple 在这一点上更清楚.但是,如果您正在处理 Objective-C 对象(包括 Cocoa 类),它们可能是自动释放对象,在这种情况下,Objective-C @autoreleasepool
模式的 Swift 版本仍然很有用.>
On page 17 of this WWDC14 presentation, it says
Working with Objective-C? Still have to manage autorelease pools
autoreleasepool { /* code */ }
What does that mean? Does it mean that if my code base doesn't have any Objective-C files, autoreleasepool {}
is unnecessary?
In an answer of a related question, there is an example where autoreleasepool
can be useful:
- (void)useALoadOfNumbers {
for (int j = 0; j < 10000; ++j) {
@autoreleasepool {
for (int i = 0; i < 10000; ++i) {
NSNumber *number = [NSNumber numberWithInt:(i+j)];
NSLog(@"number = %p", number);
}
}
}
}
If the code above gets translated into Swift with autoreleasepool
dropped, will Swift be smart enough to know that the number
variable should be released after the first }
(like some other languages does)?
The autoreleasepool
pattern is used in Swift when returning autorelease
objects (created by either your Objective-C code or using Cocoa classes). The autorelease
pattern in Swift functions much like it does in Objective-C. For example, consider this Swift rendition of your method (instantiating NSImage
/UIImage
objects):
func useManyImages() {
let filename = pathForResourceInBundle
for _ in 0 ..< 5 {
autoreleasepool {
for _ in 0 ..< 1000 {
let image = NSImage(contentsOfFile: filename)
}
}
}
}
If you run this in Instruments, you'll see an allocations graph with 5
small hills (because outer for-loop), like the following:
But if you do it without the autorelease pool, you'll see that peak memory usage is higher:
The autoreleasepool
allows you to explicitly manage when autorelease objects are deallocated in Swift, just like you were able to in Objective-C.
Note: When dealing with Swift native objects, you generally will not receive autorelease objects. This is why the presentation mentioned the caveat about only needing this when "working with Objective-C", though I wish Apple was more clear on this point. But if you're dealing with Objective-C objects (including Cocoa classes), they may be autorelease objects, in which case this Swift rendition of the Objective-C @autoreleasepool
pattern is still useful.
这篇关于是否有必要在 Swift 程序中使用 autoreleasepool?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!