UIView如何避免保留循环?

3

Subview(子视图)引用了Superview(父视图),而Superview也引用了Subview(子视图)。

我想知道为什么这不会导致循环应用?


1
一个引用是弱引用。 - rmaddy
我假设其中一个引用必须是弱引用。然而,我无法确定哪一个是弱引用。 - David Liu
对父视图的引用是弱引用。 - rmaddy
@property(nonatomic, readonly) UIView *superview 我在文档中没有看到superview是弱引用。 - David Liu
好的,所以它是“assign”,而不是“weak”。 - rmaddy
1个回答

2

UIView's superview property is declared as

@property(nonatomic, readonly) UIView *superview;

在Objective-C中,如果没有指定不同的所有权声明符,则属性默认为assignstrong,自从引入ARC以来,但是UIKit头文件似乎没有使用ARC,因此该属性最可能是assign。还要注意,由于属性是只读的,源代码中很可能有一个自定义getter,因此属性中的所有权说明符并不能告诉我们任何信息。可以安全地假设苹果已经以避免保留循环的方式实现了它。 assign等价于__unsafe_unretained,这是一个非零弱引用。这意味着它不会保留对象,但在对象被释放时不会设置为nil。这比weak具有更高的性能(因为它不需要被检查和清零),但不安全,因为如果引用的对象被释放,您可能正在访问垃圾内存。
还要注意,该属性被声明为readonly,这意味着它实际上可以被实现为返回私有实例变量的方法,或者完全执行我们不知道的其他操作。基本上,重要的是您可以假设此属性不会保留所引用的对象
在今天的新代码中,应该使用weak而不是assign

在Objective-C中,如果没有指定不同的所有权说明符,那么属性默认应该是strong,对吗?我认为实际上是因为@property(nonatomic, readonly, copy) NSArray *subviews,所以父视图不会持有子视图的保留计数,因为有了copy属性。 - David Liu
另外,assign属性不执行任何类型的内存管理。这是原始数据类型的默认行为。assign__unsafe_unretained不等同。 - David Liu
@DavidLiu __unsafe_unretainedassign 在实践中实际上是相同的,请参考这个答案 - Greg

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接