Skip to content

1、 什么是Block?

Block是将函数以及其执行上下文封装起来的对象。

2、 Block和函数指针的区别是什么?

Block和函数指针都可以用来引用代码,但主要区别在于Block可以捕获其定义环境中的变量,而函数指针不能。此外,Block是Objective-C的对象,可以加入到NSArray或NSDictionary等集合中,而函数指针是C语言的概念,不能直接存储在Objective-C的集合中。

3.Block一般用什么关键字修饰,为什么?哪些情况会引起Block循环引用,如何解决?

copy关键字修饰,因为创建block是在栈内存里面,需要通过copy放入堆内存进行管理。

一个对象强引用了block,在block中又强引用了该对象,就会形成循环引用;可以在block引用A时使用weak解决。

4、 如何避免Block中的循环引用?

在Block内部使用外部对象时,如果直接引用这些对象,可能会导致循环引用,特别是当Block被对象持有时。为了避免这种情况,可以使用__weak__block修饰符来声明外部变量。__weak修饰符可以创建一个弱引用,它不会增加对象的引用计数。__block修饰符用于可变变量或在Block内部需要修改的变量。

5、 Block的内存管理是如何工作的?

Block默认是在栈上创建的,当Block作为函数返回值时,它会自动复制到堆上。如果Block被赋值给__strong指针或者被Objective-C容器类持有,同样会被复制到堆上。在堆上的Block需要手动管理内存(在非ARC环境下),或者在ARC环境下自动管理。复制到堆上的Block会捕获其使用的所有外部变量的副本。

6、 举个使用Block的例子。

Block在iOS开发中经常用于处理异步任务的回调。例如,我们可以使用Block来处理网络请求的响应:

objective-c
[self fetchDataFromServerWithCompletion:^(NSData *data, NSError *error) {
    if (error) {
        NSLog(@"Error: %@", error);
    } else {
        NSLog(@"Data received: %@", data);
    }
}];

在这个例子中,fetchDataFromServerWithCompletion:方法接受一个Block作为参数,这个Block用于处理网络请求完成后的数据或错误。

这些问题和答案应该能够帮助面试者理解和回答有关Block的面试题。

7.Block的几种形式

  • 全局Block :不使用外部变量的Block是全局Block
  • 栈Block :使用外部变量且未进行copy操作的Block是栈Block
  • 堆Block :对栈Block进行copy操作的的Block是堆Block;而对全局Block操作后仍然是全局Block

世界很美 而你正好有空