block内部实现原理(一)
【block 定义】
block是iOS4.0+ 和Mac OS X 10.6+ 引进的对C语言的扩展,用来实现匿名函数的特性。
【block 结构】
【block原理】
1.一个简单block
以一个简单block为例, Clang提供了中间代码展示的选项供我们进一步了解block的原理。
在Terminal, 使用-rewrite-objc选项编译:
得到一份main.cpp文件,open这份文件中可以看到如下代码片段:
从命名可以看出这是block的实现,并且得知block在Clang编译器前端得到实现,可以生成C中间代码。
2 . 首先,返回值类型 (void (*)() 空指针,
参数__main_block_func_0,参数&__main_block_desc_0_DATA,以及用来调用的__main_block_impl_0。
__main_block_func_0是一个函数,__main_block_desc_0_DATA,__main_block_impl_0则是一个结构体,
生成的代码片段如图:
所以说 实际上block就是指向结构体的指针。
__main_block_impl_0中包含了两个成员变量和一个构造函数,成员变量分别是__block_impl结构体和描述信息Desc,之后在构造函数中初始化block的类型信息和函数指针等信息。
接着出现的是__main_block_func_0函数,即block对应的函数体。该函数接受一个__cself参数,即对应的block自身。
再下面是__main_block_desc_0结构体,其中比较有价值的信息是block大小。
main函数在最后,最后就是main函数中对block的创建和调用,可以看出执行block就是调用一个以block自身作为参数的函数,这个函数对应着block的执行体。
这里,block的类型用_NSConcreteStackBlock来表示,表明这个block位于栈中。同样地,还有_NSConcreteMallocBlock和_NSConcreteGlobalBlock。
3. 从上面代码看出,
isa指针:指向表明该block类型的类。
flags:按bit位表示一些block的附加信息,比如判断block类型、判断block引用计数、判断block是否需要执行辅助函数等。
funcPtr: 是block对应的函数指针
desc:block的附加描述信息,比如保留变量数、block的大小、进行copy或dispose的辅助函数指针。
reserved:保留变量,我的理解是表示block内部的变量数。
size: block大小
未完待续