今天整理了一下关于block的问题总结,
block 说白了就是代码块,在Swift里面叫作闭包,block 只是 Objective-C 对闭包的实现,并不是 iOS 独有的概念,在 C++、Java 等语言也有实现闭包,名称不同而已,将同一逻辑的代码放在一个块,使代码更简洁紧凑,广受开发者欢迎。但同时 block 也是 iOS比较难理解的地方,因此有必要了解下 block 的实现原理,知其然,更知其所以然,才能从根本上避免挖坑和踩坑。
block 结构体信息详解
struct __block_impl
// __block_impl 是 block 实现的结构体
struct __block_impl
{
void *isa;
int Flags;
int Reserved;
void *FuncPtr;
};
isa
指向实例对象,表明 block 本身也是一个 Objective-C 对象。block 的三种类型:_NSConcreteStackBlock、_NSConcreteGlobalBlock、_NSConcreteMallocBlock,即当代码执行时,isa 有三种值
impl.isa = &_NSConcreteStackBlock;
impl.isa = &_NSConcreteMallocBlock;
impl.isa = &_NSConcreteGlobalBlock;
Flags
按位承载 block 的附加信息;
Reserved
保留变量;
FuncPtr
函数指针,指向 Block 要执行的函数,即{ printf("Block\n") };
struct __main_block_impl_0
// __main_block_impl_0 是 block 实现的结构体,也是 block 实现的入口
struct __main_block_impl_0
{
struct __block_impl impl;
struct __main_block_desc_0* Desc;
__main_block_impl_0(void *fp, struct __main_block_desc_0 *desc, int flags=0)
{
impl.isa = &_NSConcreteStackBlock;
impl.Flags = flags;
impl.FuncPtr = fp;
Desc = desc;
}
};
impl
block 实现的结构体变量,该结构体前面已说明;
Desc
描述 block 的结构体变量;
__main_block_impl_0
结构体的构造函数,初始化结构体变量 impl、Desc;
了解了block的结构体,我么来说说具体的用法:
1. 最常用的用法就是访问外部变量: