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类之间是否存在保留周期? 在这种情况下,它可能是一个保留周期?如果

我需要一些关于Swift中闭包中引用的解释。 这是我的用例,让我们想象一下:

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