weak的实现原理
面试的时候我们经常会被问到,项目中用过weak吗,用在哪些地方啊,该怎么使用啊。相信很多小伙伴都用过weak,可能也有很多小伙伴对于weak的使用原理不是很清楚,我就讲一下我自己对weak的理解吧,如有错误,欢迎指正,共同学习。
1.先说说weak的使用场景
(1).用的最多的大概就是代理了吧!先上一段代码
@protoco CMBombViewDelegate<NSObject>
- (void)bombViewRightBtnClickBlock:(CMBombView*)bombView;
@optional
- (void)bombViewLeftBtnClickBlock:(CMBombView*)bombView;
@end
@property (nonatomic, weak) id <CMBombViewDelegate>delegate;
这里为啥用weak了,因为weak:指明该对象并不负责保持delegate这个对象,delegate这个对象的销毁由外部控制。如果用strong修饰的话,strong:该对象强引用delegate,外界不能销毁delegate对象,会导致循环引用(Retain Cycles),也就是死循环。
面试的时候,大部分人被问到的时候,能打出weak是弱引用。能够输出weak表实际是个哈希表的不多。
weak 实现原理的概括
Runtime维护了一个weak表,用于存储指向某个对象的所有weak指针。weak表其实是一个hash(哈希)表,Key是所指对象的地址,Value是weak指针的地址(这个地址的值是所指对象的地址)数组。
weak 的实现原理可以概括一下三步:
1、初始化时:runtime会调用objc_initWeak函数,初始化一个新的weak指针指向对象的地址。
2、添加引用时:objc_initWeak函数会调用 objc_storeWeak() 函数, objc_storeWeak() 的作用是更新指针指向,创建对应的弱引用表。
3、释放时,调用clearDeallocating函数。clearDeallocating函数首先根据对象地址获取所有weak指针地址的数组,然后遍历这个数组把其中的数据设为nil,最后把这个entry从weak表中删除,最后清理对象的记录。
如果面试的时候能够答出这些,都会是加分项的,祝愿每个小伙伴都能拿到高薪。