考虑以下代码:
class Foo
{
}
func foo() -> (Void -> Foo)
{
var foo = Foo()
return { foo }
}
var fooGen = foo()
现在,每当我调用
fooGen
时,都会获取存储的Foo
实例。但是,存储foo
的确切位置是什么?它在烟囱里吗?如果是这样,那它的一生是什么? 最佳答案
类和闭包都是引用类型。
var foo = Foo()
在堆上创建一个
Foo
对象,并存储一个(强)在本地堆栈变量
foo
中引用该对象。return { foo }
创建一个捕获
foo
的闭包,以便闭包保持对该对象的另一个(强)引用。
从函数返回时,局部变量
foo
超出范围,对于这一点,只有一个来自结束的参考仍然存在。
var fooGen = foo()
引用返回的闭包
对
fooGen
对象的引用):fooGen -> closure -> Foo object
因此只要存在
Foo
引用,对象就存在。(假设没有创建其他强引用)。
演示:
class Foo
{
deinit {
println("deinit")
}
}
func foo() -> (Void -> Foo)
{
var foo = Foo()
return { foo }
}
if true {
var fooGen = foo()
println("foo")
}
println("done")
输出:
福
德尼特
完成
当程序控制离开
Foo
范围时,对象将被销毁。