#import
int main(int argc, const
char * argv) ;
i = 3;
myblock ();
}return
0;}
執行結果:i的值是:2
為什麼是2 不是3呢?帶著這個疑問我們往下看
編譯main.m檔案,1.開啟終端,2.找到工程檔案,3.找到main.m檔案所在的位置,4.clang -rewrite-objc main.m重新編譯會生成乙個main.cpp的檔案。這個檔案相當大滑倒檔案底部找到如下**
int main(int argc, const char * argv)
return 0;
}
由上面的**我們看到block被轉化為了__main_block_impl_0的結構體例項
struct
__main_block_impl_0
};
desc :描述 block 的結構體變數;
i:引數
__main_block_impl_0 :結構體的建構函式,初始化結構體變數 impl、desc;
impl:__block_impl 是 block 實現的結構體
struct __block_impl ;
isa:指向例項物件,說明 block 本身也是 objective-c 物件;
flags:按位承載 block 的附加資訊;
reserved :保留變數;
funcptr:函式指標,指向 block 要執行的函式,即 __main_block_func_0;
static
void __main_block_func_0
// __main_block_func_0 是 block 要最終要執行的函式**
static
void __main_block_func_0(struct __main_block_impl_0 *__cself)
__main_block_impl_0型別的引數__cself在__main_block_func_0內部copy了乙份i,我們列印的實際上是新複製的這乙份,所以block內部的i和外部的i不是同乙份,不論外部i怎麼變化,對block內部都沒有影響,也就解釋了為什麼列印結果是2不是3
static
struct __main_block_desc_0 __main_block_desc_0_data = ;
reserved :結構體資訊保留字段
block_size :結構體大小
此處已定義了乙個該結構體型別的變數 __main_block_desc_0_data
#import
int main(int argc, const
char * argv) ;
i = 3;
myblock ();
}return
0;}
執行結果:i的值是:3
這又是為什麼呢?咱們繼續往下看
clang -rewrite-objc main.m 開啟main.cpp 找到如下**
int main(int argc, const char * argv) ;
void (*myblock)() = ((void (*)())&__main_block_impl_0((void *)__main_block_func_0, &__main_block_desc_0_data, (__block_byref_i_0 *)&i, 570425344));
(i.__forwarding->i) = 3;
((void (*)(__block_impl *))((__block_impl *)myblock)->funcptr)((__block_impl *)myblock);
}return 0;
}
我們發現只是在引數i前面加__block,i的定義變複雜了很多,i 是__block_byref_i_0型別的結構體
struct __block_byref_i_0 ;
__isa :指向例項物件,表明i是oc的物件,不再是基本資料型別
__forwarding:指向自己的指標
void (*myblock)() = ((void (*)())&__main_block_impl_0((void *)__main_block_func_0, &__main_block_desc_0_data, (__block_byref_i_0 *)&i, 570425344));
main_block_impl_0 中引用的是 block_byref_i_0 的結構體指標
struct
__main_block_impl_0
};
從__main_block_impl_0結構體看到:i(_i->__forwarding),i的值是通過__forwarding指標取到的, (i.__forwarding->i) = 3;
修改的也是__forwarding指向的block_byref_i_0結構體中的i,所以列印結果為3
在寫的過程中參考了如下文章,謝謝文章作者
block的實現
Block中 block實現原理
三.block中 block實現原理 我們繼續研究一下 block實現原理。1.普通非物件的變數 先來看看普通變數的情況。import int main int argc,const char ar myblock return 0 把上述 用clang轉換成原始碼。struct block byr...
block的實現原理
main.m import block實際上是 指向結構體的指標 編譯器會將block的內部 生成對應的函式 void test1 block func 0 void test1 a 20 block 10 void test2 a 20 block 20 void test3 a 20 block...
block實現原理詳解
對於大多數人來講,block內部到底是怎樣實現的呢?我們可以借助clang將其編譯成為c 的 就可以看出,block到底是什麼東西,先來看這樣乙個問題,int age 10 void block age 30 block 10 以及下面的這一段 block int age 10 void block...