在创建一个block类型的属性时,经常会看到这个属性被加上了copy
关键字,例如:
1 | @property (nonatomic,copy) MyBlock block; |
这是为什么呢?
首先,block有三种:
- _NSConcreteStackBlock
- _NSConcreteGlobalBlock
- _NSConcreteMallocBlock
_NSConcreteStackBlock设置在栈上.
_NSConcreteGlobalBlock设置在程序的数据区域,和全局变量一样.
_NSConcreteMallocBlock分配在堆中.
当一个block设置在栈中时,如果其所属的作用域结束,该block就被废弃.如果一个方法需要返回一个block,如何解决这个问题呢?
block提供了将其复制到堆上的方法来解决这个问题.
1 | typedef int (^blk_t)(int); |
1 | typedef int (^blk_t)(int); |
在ARC中,block在被返回前自动被copy一次,直接return就行.然而,block作为参数时,需要手动copy
1 | -(id) getBlockArray{ |
另外,block有自动捕获变量的功能,当一个block被copy时,其自动捕获的变量也被复制到堆中,并且被block持有.