Swift 封闭解释中的强、弱、无主自我
我需要一些关于Swift中闭包中引用的解释。 这是我的用例,让我们想象一下:Swift 封闭解释中的强、弱、无主自我,swift,closures,automatic-ref-counting,Swift,Closures,Automatic Ref Counting,我需要一些关于Swift中闭包中引用的解释。 这是我的用例,让我们想象一下: class A {...} class B { func makeAclosure() { let instanceA = A() instanceA.someFunctionA(completion: {(input) in self.someAnotherFunction(input) }) } } a类和B类之间是否存在保留周期? 在这种情况下,它可能是一个保留周期?如果
class A {...}
class B {
func makeAclosure() {
let instanceA = A()
instanceA.someFunctionA(completion: {(input) in
self.someAnotherFunction(input)
})
}
}
a类和B类之间是否存在保留周期?
在这种情况下,它可能是一个保留周期?如果在调用闭包之前您的
self
对象可能会被释放,那么您应该指定[弱self]
,这样您就可以避免错误的访问异常
如果您知道它肯定不会被解除分配,那么您可以使用[unowned self]
创建一个行为类似于隐式展开的可选对象的引用
在您的示例中,B
的实例拥有对instanceA
的引用(在您的makeAClosure()
函数的上下文中),因此您不会以retain循环结束
您应考虑执行<代码>某个函数(完成:)/代码>,以确定是否需要<代码>未拥有的< /代码>或<代码>弱在该闭包中引用<代码>自我>代码>
(旁白:如果您使用的是
[弱自我]
,那么为了避免在整个代码中使用诸如self?
之类的选项,您可以使用guard let`self`=self-else{…}
继续在闭包代码中使用self
。如果在调用闭包之前您的self
对象可能会被解除分配,您应该指定[弱self]
,以避免出现错误的访问异常
如果您知道它肯定不会被解除分配,那么您可以使用[unowned self]
创建一个行为类似于隐式展开的可选对象的引用
在您的示例中,B
的实例拥有对instanceA
的引用(在您的makeAClosure()
函数的上下文中),因此您不会以retain循环结束
您应考虑执行<代码>某个函数(完成:)/代码>,以确定是否需要<代码>未拥有的< /代码>或<代码>弱在该闭包中引用<代码>自我>代码>
(旁白:如果您使用的是
[弱自我]
,那么为了避免在整个代码中使用诸如self?
之类的选项,您可以使用guard let`self`=self-else{…}
继续在闭包代码中使用self
。如果不看A.somefunction
,就不可能说,因为如果完成是@escaping
(例如,如果它被保留),则不知道它是@escaping
Swift需要确保运行时的安全性,并通过强烈引用self
(因为self
是闭包中使用的唯一变量)使将来可能需要的任何对象保持活动状态
在这种情况下,没有引用循环。这是因为instanceA
没有被保留,所以A=>B,但是B!=>A
但是,如果instanceA
被B
保留(假设您创建了instanceA:A
属性并对其进行了设置),那么您将有一个保留周期
为了解决这个问题,您可以在闭包中创建变量弱
或无主
。它们都做相同的事情,但提供的类型略有不同。它们都持有弱引用,这意味着instanceA
不会增加B
实例的引用计数;如果B
>已解除分配,并且没有其他引用,instanceA
也已解除分配
使用[弱自我]
自我
是可选的
,例如自我:B?
。但是,[无主自我]
是显式展开的,例如self:B!
。这意味着如果调用闭包且self
为nil
时,您的程序将崩溃。这就是为什么当您确定解除分配B
也将解除分配A
时,仅使用无主非常重要。有几种情况s其中无主
是安全的,例如,创建闭包并将其存储在创建闭包的同一对象上时,但这有更多细微差别
如果不确定,请使用weak
!不看A.somefunction
就不可能说,因为如果完成
是@escaping
(例如,如果它被保留),这是未知的。对于剩下的答案,我将假定它是@escaping
Swift需要确保运行时的安全性,并通过强烈引用self
(因为self
是闭包中使用的唯一变量)使将来可能需要的任何对象保持活动状态
在这种情况下,没有引用循环。这是因为instanceA
没有被保留,所以A=>B,但是B!=>A
但是,如果instanceA
被B
保留(假设您创建了instanceA:A
属性并对其进行了设置),那么您将有一个保留周期
为了解决这个问题,您可以在闭包中创建变量弱
或无主
。它们都做相同的事情,但提供的类型略有不同。它们都持有弱引用,这意味着instanceA
不会增加B
实例的引用计数;如果B
>已解除分配,并且没有其他引用,instanceA
也已解除分配
当使用[弱自我]
时,self
是可选的
,例如self:B?
。但是,[无主自我]
是显式展开的,例如self:B!
。这意味着如果调用了闭包并且self
是nil
,您的pr