美文网首页
block中weakself、strongself 的引用规范

block中weakself、strongself 的引用规范

作者: 傲弛天下 | 来源:发表于2017-02-06 13:59 被阅读0次

    项目中的宏定义
    <pre>

    define kSelfWeak __weak typeof(self) weakSelf = self

    define kSelfStrong __strong typeof(weakSelf) strongSelf = weakSelf

    </pre>

    正常我们在使用block时会写出如下的代码:
    <pre>

    • (void)function{
      kSelfWeak; //创建一个指向当前对象的弱引用
      [teseObject callFunc:^{
      kSelfStrong; //block内部定义一个指向当前对象的强引用
      [strongself callFunc_1:....];
      [strongself callFunc_2:....];
      ....
      }];
      }
      </pre>

    现在我们来带着问题分析一下上面的这个代码:

    1. 可不可以直接使用self?
      不可以。因为这样block会强持有self对象,造成循环引用,从而导致内存泄露。

    2. 可不可以直接使用weakself?
      看情况。由于weakself不会持有对象,因此不会造成循环引用的问题,但是使用weakself却会造成block执行不一致问题,试想一下上面的代码,当调用“callFunc_1”的时候weakself是有效的,但是当调用“callFunc_2”的时候weakself可能已经是nil了,这样就造成了block内执行不一致从而导致意想不到的结果

    3. 循环引用是不是都是坏人?
      答案是否定的。当block开始执行的时候,strongself会去取self对象的值,如果此时self已经为nil,那么整个block执行期间strongself都是nil,如果self有效那么strongself就是利用了循环引用的特性保证了在block执行的时候self对象不会被析构,保证block执行的一致性。其实我们在编写业务代码的时候(很多第三方开源类库)中会利用到循环引用的这一特性来保证block中引用的对象在block执行的时候依然有效,但是切忌使用这样黑魔法的时候要在block执行结束后打破循环引用。由于strongself是block内部定义的变量,在block执行结束会由系统回收从而打破循环引用

    <pre>
    总结:使用strongself可以消除循环引用带来的内存泄漏,也可以保证block执行过程中的一致性。所以正常的业务代码我们都会使用上面的标准方式编写,只有特殊的情况才会利用block的特性写一些黑魔法的代码。
    </pre>

    更多原理:http://www.jianshu.com/p/a5dd014edb13

    相关文章

      网友评论

          本文标题:block中weakself、strongself 的引用规范

          本文链接:https://www.haomeiwen.com/subject/suzyittx.html