只是想确保我做对了:
__unsafe_unretain
我不拥有的对象吗?__unsafe_unretained
我是否需要在assign
中使用@property
?这是否意味着不保留对象,只是引用我分配给的对象?答案 0 :(得分:185)
LLVM编译器3.0引入了四个新的所有权限定符:__strong
,__autoreleasing
,__unsafe_unretained
和__weak
。根据{{3}},即使在ARC之外,前三个也可用。
正如Joshua指出的那样,默认情况下,所有指针都隐含在ARC下__strong
。这意味着当一个对象被分配给该指针时,只要该指针引用它,它就会被保留。对于大多数事情来说这很好,但它为保留周期开辟了可能性,正如我在回答the specification中所描述的那样。例如,如果您有一个包含另一个对象作为实例变量的对象,但该第二个对象具有一个强大的链接返回到第一个对象作为其委托,则这两个对象将永远不会被释放。
出于这个原因,__unsafe_unretained
和__weak
限定符存在。最常见的用途是代表,您可以使用weak
或unsafe_unretained
属性(assign
实际上是unsafe_unretained
)为该代理人定义属性,并且然后通过用__weak
或__unsafe_unretained
标记相应的实例变量来匹配。这意味着委托实例变量仍将指向第一个对象,但它不会导致保留该对象,从而打破保留周期并允许释放两个对象。
除了代理之外,这对于破坏代码中可能形成的任何其他保留周期非常有用。有用的是,Leaks仪器现在包含一个Cycles视图,它以图形方式显示它在应用程序中发现的保留周期。
__unsafe_unretained
和__weak
都会阻止对象的保留,但方式略有不同。对于__weak
,指向对象的指针将在它指向的对象的解除分配时转换为nil
,这是非常安全的行为。顾名思义,__unsafe_unretained
将继续指向对象所在的内存,即使它已被释放。由于访问了已释放的对象,这可能导致崩溃。
为什么你会使用__unsafe_unretained
呢?不幸的是,__weak
仅支持iOS 5.0和Lion作为部署目标。如果你想回到iOS 4.0和Snow Leopard,你必须使用__unsafe_unretained
限定符,或使用Mike Ash的here之类的东西。
答案 1 :(得分:4)
weak
用于您不拥有的对象。unsafe_unretained
。unsafe_unretained
项与weak
类似,没有额外的安全性,当它们指向的项目被释放时清除它们(以及随之而来的开销)。答案 2 :(得分:4)
__unsafe_unretained
与ARC之前的对象的默认存储相同。使用ARC时,默认值为__strong
,这意味着您可以引用它,直到您的引用超出范围。
答案 3 :(得分:1)
__unsafe_unretained的另一个观察结果:我的设备上的应用程序崩溃,模拟器上的不,iVars声明为__unsafe_unretained! 是的,它是ARC迁移代码中的一个错误,但这是我第一次注意到设备和模拟器之间存在这样的差异。