Swift中的关联对象,全局键实际上是否生成特定的实例?

要在Swift中拥有关联对象,只需使用内存地址作为句柄,然后使用objc调用。

通常的示例代码,你可以谷歌无处不在:

var keyA:UInt8 = 0 var keyB:UInt8 = 0 extension UIViewController { var aoAA: String? { get { return objc_getAssociatedObject(self, &keyA) as? String } set { objc_setAssociatedObject(self, &keyA, newValue, objc_AssociationPolicy.OBJC_ASSOCIATION_RETAIN) } } var aoBB: String? { get { return objc_getAssociatedObject(self, &keyB) as? String } set { objc_setAssociatedObject(self, &keyB, newValue, objc_AssociationPolicy.OBJC_ASSOCIATION_RETAIN) } } } 

这工作正常,

 class Thing: UIViewController { override func viewDidLoad() { super.viewDidLoad() aoAA = "this is a" print("...... \(aoAA)") aoBB = "this is b" print("...... \(aoBB)") aoAA = "changed A" print("...... \(aoAA) \(aoBB)") aoBB = "changed B" print("...... \(aoAA) \(aoBB)") aoAA = aoBB print("...... \(aoAA) \(aoBB)") } 

可是等等…

整个项目的句柄(keyA和keyB) 是全局的

当你在不同的 UIViewController中使用aoAA和aoBB时,aoAA和aoBB怎么可能作为那个特定的属性?

项目中到处都只有“一个”aoAA?

即,aoAA是一个全球性的 – 正如处理keyA是一个全球性的?

我的testing似乎表明,它们独立的variables,特定于不同的UIViewControllers的不同实例,但这似乎很糟糕。

aoAA每个实例aoAA可能不同 – 它使用相同的全局句柄?

Objective-C的“关联对象”概念允许您将一个“目标”对象实例与一个“源”对象实例连接起来。 这是一个单向的联系,只有来源知道目标:

关联对象与源和目标实例

 objc_setAssociatedObject(source, key, target, ...) 

该关联使用一个键能够连接和区分任何数量的关联对象与一个来源。 键必须明显不同 – 但只适用于一个源实例。

因为您必须提供密钥和源实例来检索关联的对象,所以没有必要使用真正唯一的密钥。 objc_***AssociatedObject的实现可以通过组合实例指针和键来形成一个进程唯一键。

所以对于你的例子,是的,即使keyAkeyB是全局的, aoAAaoBB都会为每个UIViewController实例返回单独的值。

要清楚地说明,给定扩展中的每个关联对象需要不同的键。 所以, aoAAaoBB都需要自己的密钥,如示例代码所示(也就是keyAkeyB的指针)。 但正如在问题中所提到的那样, 每个关联对象只有一个关键字,不pipe这个关系使用了多less符合类。