问题一: block对象的生命周期?
直接看代码,打印结果是什么?
#import <Foundation/Foundation.h> //定义block对象(全局block) int (^externBlock)(void) = ^(void){return 100;}; //定义函数(block做为参数) void function(int (^block)(void)) { printf("执行block的结果是:%d\n\n", block()); } //定义的两个函数 void firstFunc(int number) { //定义块对象(局部) int (^blockWithinFirst)(void) = ^(void) { return number; }; //调用外部的function函数 function(blockWithinFirst); //赋值 externBlock = blockWithinFirst; } void secondFunc(int number) { //int局部变量 int index = 10; //block局部对象 int (^blockWithinSecond)(void) = ^(void) {return number * index;}; //调用外部function函数 function(blockWithinSecond); } int main(int argc, const char * argv[]) { @autoreleasepool { //1.调用function函数 function(externBlock); //2.调用firstFunc firstFunc(5); //3.调用secondFunc secondFunc(10); //4.和步骤1一样 function(externBlock); } return 0; }
问题二:Block体中访问全局变量/局部静态变量/局部变量的问题,如何解决(考察__block类型)
#import <Foundation/Foundation.h> void function(int number, void (^blockParam)(void)) { //打印传入的number值 printf("传入的number是: %d\n", number); //调用传入的block对象 blockParam(); } int globalNumber = 1000;//全局变量(外部变量) int main(int argc, const char * argv[]) { @autoreleasepool { //块声明(没有传参,没有返回值) void (^internalBlock)(void); //局部静态变量 static int localStaticInt = 20; //局部变量:local variable(自由变量:free variable) int localInt = 20; //第一部分:将block对象最为函数的参数,在函数内部调用block //块定义(打印上面三个变量的值); internalBlock = ^(void) { printf("全局变量globalNumber:%d; 局部静态变量localStaticInt:%d; 局部变量localInt:%d\n", globalNumber, localStaticInt, localInt); }; //将internalBlock块对象作为function的参数,调用function函数 function(1, internalBlock); //第二部分:修改上述三个变量的值,重新调用function函数 globalNumber = 3000; localStaticInt = 0; localInt = 0; function(2, internalBlock); //第三部分:重新再写一次block的定义部分,再调用function函数 internalBlock = ^(void) { printf("全局变量globalNumber:%d; 局部静态变量localStaticInt:%d; 局部变量localInt:%d\n", globalNumber, localStaticInt, localInt); }; function(3, internalBlock); //第四部分:考察__block类型修饰问题 __block int localAnotherInt = 20; void (^firstBlock)(void) = ^(void) { globalNumber += 100; localStaticInt += 200; localAnotherInt = 10; printf("重新赋值后的globalNumber:%d;localStaticInt:%d; localAnotherInt:%d\n\n", globalNumber, localStaticInt,localAnotherInt); }; //调用/执行firstBlock firstBlock(); } return 0; }
分析:
初始化:全局:1000; 局部静态:20; 局部变量:20
a. function(1, internalBlock); 包除了包含可执行的代码,还包含可访问的变量的值(全局:1000; 局部静态:20; 局部变量:20)
b. globalNumber = 3000;
localStaticInt = 0;
localInt = 0;
function(2, internalBlock);
包除了包含可执行的代码,还包含可访问的变量的值(全局:3000; 局部静态:0; 局部变量:20);原因是block体内对局部变量没有修改的权限,还是原来第一次执行的包的数据
c. 重新再定义internalBlock块对象, 此时包内就重新包含了新的值(全局:1000; 局部静态:0; 局部变量:0)
internalBlock = ^(void) { printf("全局变量globalNumber:%d; 局部静态变量localStaticInt:%d; 局部变量localInt:%d\n", globalNumber, localStaticInt, localInt); };
function(3, internalBlock);
d.如果把局部的变量的类型添加__block类型,可以在block体中修改局部变量的值(重新赋值后的globalNumber:3100;localStaticInt:200; localAnotherInt:10)
问题三:Block体循环应用的问题,如何解决(考察__weak类型)
TRBlockObject *blockObj = [TRBlockObject new]; blockObj.block = ^void(void){ NSLog(@"blockObj%@“,blockObj); };
例子中,block属性是blockObj对象的;而在block体中,block又引用了blockObj对象,造成了循环引用。
解决的办法是:
TRBlockObject *blockObj = [TRBlockObject new]; //解决循环引用的方案使用__weak修饰符。 __weak TRBlockObject *weakBlockObj = blockObj; blockObj.block = ^void(void){ NSLog(@"blockObj%@",weakBlockObj); };
__weak是弱引用,blockObj被释放的时候,weakBlockObj已经是nil了。
免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。