iOS中的Block

Block的种类

  • NSConcreteGlobalBlock
    Block内部没有引用外部变量时,block的类型就是GlobalBlock,而且GlobalBlock是全局block,保存在程序数据区(.data区域)如下图所示
    iOS中的Block_第1张图片
    594FD12E-4FFA-4CCB-8DD9-2E5C856B7673.png
  • NSConcreteStackBlock
    顾名思义它是保存到栈上,当Block引用了外部局部变量时,block的类型就是StackBlock,如下图所示


    iOS中的Block_第2张图片
    5D35F538-9048-470C-8413-BEAACB919CEE.png

但GlobalBlock和StackBlock区别在哪里呢?实际上stackBlock会在block内部用一个结构体__main_block_impl_0保存外部变量,但没有对外部对象持有引用,所以变量引用计数不变。
注意一点
关于block引用外界变量的问题,其实也分很多情况,比如引用的外界变量是static修饰的变量或者全局变量的话,它依然是GlobalBlock。

  • NSConcreteMallocBlock
    当block进行了copy操作时,block的类型就变成MallocBlock,这时它保存到堆上,注意MallocBlock会持有外部变量
    iOS中的Block_第3张图片
    6A4F3690-50C8-400C-81C6-469E5D985E53.png
  • 关于block
    我们知道,变量用__block修饰可以在block内部更改变量的值,原因在于存在栈上的变量拷贝到堆上。
    注意!!这里需要知道的是,在MRC环境下,如果没有用__block,会对外部对象采用copy的操作,而用了__block则不会用copy的操作。
    而在ARC环境下,对于声明为__block的外部对象,在block内部会进行retain,以至于在block环境内能安全的引用外部对象,所以要谨防循环引用的问题

  • 关于循环引用
    一句话可以概括:判断持有block的对象是否也被block持有,如果有则出现循环引用。

Ref
让我们来深入浅出block吧 -
block使用小结、在arc中使用block、如何防止循环引用 - CSDN博客
Block基础和retain cycle(循环引用) -
谈Objective-C block的实现 | 唐巧的博客
__block存储类型 - Nonato - 博客园
Block 原理详解 - CSDN博客
Block基础和retain cycle(循环引用) -
block没那么难(三):block和对象的内存管理 - 作业部落 Cmd Markdown 编辑阅读器
正确使用Block避免Cycle Retain和Crash - Cooper’s Blog
【小测试】你真的知道blocks在Objective-C中是怎么工作的吗?(获奖公布) | 灌水大厅 - CocoaChina CocoaChina_让移动开发更简单
clang -rewrite-objc的使用点滴

你可能感兴趣的:(iOS中的Block)