iOS Block初探
2018-02-05 本文已影响5人
小生图图
block:具有自动变量的匿名函数
下列场景会retain:
1.引用局部变量
2.引用self的成员变量,self会被retain
block作用域:
1.全局block:block未使用任何变量或只使用了全局变量,则block放在全局区
2.栈区block:MRC下会把使用了局部变量(自动变量)的block放在栈区
3.堆区block:ARC下会把使用了局部变量(自动变量)的block放在堆区,MRC下栈区block发生拷贝时也会放在堆区
__block修饰符:
1.基本数据类型变量添加__block后,可以在block里面修改该变量的值,此时不会发生值捕获。
2.对象添加__block后不会被retain,并且可以在block里面修改。
block拷贝:
1.全局block拷贝时不会有任何操作,因为他的作用域是整个app,生命周期贯穿于整个app的生命周期,所以也没必要。
2.栈区block拷贝时会把栈区的block拷贝一份到堆区(记住是拷贝,不是所谓的移到堆区)。
3.堆区block拷贝时会增加block的引用计数(+1)。
拷贝时__block变量的存储机制:
我们在修改栈区的__block变量时,堆区的__block变量的值也会同步改变,本质上是因为变量底层机制会转换为结构体,结构体里面有一个__forwarding指针,当没有发生拷贝操作时,该指针指向自身,当发生栈到堆的拷贝时,__forwarding会指向堆区的__block变量,而堆区的__block变量的__forwarding指针则指向自身,这样当我们改变栈区的__block变量时内部就能找到堆区对应的__block变量同步改变。
有人可能会问,那我要是改变堆区的__block变量时,栈区的__block变量会改变吗,其实这样问说明还没有真正弄懂拷贝时咋回事,既然是拷贝那实现肯定只有一份了,那就只可能存在栈那边的block发生改变,堆区的这个只是拷贝了一份而已。