YYWeaKProxy的学习

图片来之网络

查看了YYWeakProxy的代码,仅仅是重载了父类的方法,将输入的target保存为实例变量,然后返回self。在YYKit中的使用地方有:
YYAnimatedImageView中151行

_link = [CADisplayLink displayLinkWithTarget:[YYWeakProxy proxyWithTarget:self] selector:@selector(step:)];

YYWebImageOperation.m的306行

_connection = [[NSURLConnection alloc] initWithRequest:_request delegate:[YYWeakProxy proxyWithTarget:self]];

YYLabel.m的143行:

_longPressTimer = [NSTimer timerWithTimeInterval:kLongPressMinimumDuration
                                              target:[YYWeakProxy proxyWithTarget:self]
                                            selector:@selector(_trackDidLongPress)
                                            userInfo:nil
                                             repeats:NO];

等等。

主要是使用在传入self时,方法会对self进行强引用。使用YYWeakProxy是为了解决强引用的问题。
强引用引起的问题是,因为一般NSTimer的invalidate方法是放在dealloc方法中去执行,而RunLoop已经强引用了NSTimer,所以当界面已经被摧毁时,而因为self被NSTimer强引用,NSTimer被RunLoop引用,所以不会执行dealloc方法。因为不执行dealloc方法,导致invalidate不会被执行。此时self就会内存泄露了。
使用了YYWeakProxy后,当界面被摧毁时,因为NSTimer没有引用self,而是引用了YYWeakProxy。所以可以执行dealloc方法,此时在dealloc中执行了invalidate。这样就会解除NSTimer对YYWeakProxy的强引用。最终self,NSTimer和YYWeakProxy也都得到了释放,内存没有被泄露。

为何YYWeakProxy能够实现呢,今天看到了回答的最好的答案:原文章


NSProxy本身是一个抽象类,它遵循NSObject协议,提供了消息转发的通用接口,NSProxy通常用来实现消息转发机制和惰性初始化资源。不能直接使用NSProxy。需要创建NSProxy的子类,并实现init以及消息转发的相关方法,才可以用。

YYWeakProxy继承了NSProxy,定义了一个弱引用的target对象,通过重写消息转发等关键方法,让target对象去处理接收到的消息。在整个引用链中,Controller对象强引用NSTimer/CADisplayLink对象,NSTimer/CADisplayLink对象强引用YYWeakProxy对象,而YYWeakProxy对象弱引用Controller对象,所以在YYWeakProxy对象的作用下,Controller对象和NSTimer/CADisplayLink对象之间并没有相互持有,完美解决循环引用的问题。


// END

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • NSTimer是iOS最常用的定时器工具之一,在使用的时候常常会遇到各种各样的问题,最常见的是内存泄漏,通常我们使...
    bomo阅读 4,996评论 0 7
  • 之前要做一个发送短信验证码的倒计时功能,打算用NSTimer来实现,做的过程中发现坑还是有不少的。 基本使用 NS...
    WeiHing阅读 9,821评论 1 8
  • 再一次面试中被问到nstimer的争取使用方法,原理,我当时就说了[_timer invalidate],time...
    iOS开发小平哥阅读 9,521评论 1 13
  • “你是宋小柔?” “嗯,是的,你是刘先生吧。” “是,很高兴见到你。喝点什么呢?” “美式,加一点奶,谢谢”宋小柔...
    长安小炸毛阅读 2,828评论 0 0
  • update-rc.d : install and remove System-V style init scri...
    printf_K阅读 2,953评论 0 0