Block面试相关问题

本文深入探讨了Block的概念,包括__block修饰符的作用、Block的三种存储形式(全局、栈、堆)以及Block如何捕获变量。重点讨论了Block导致的循环引用问题,特别是__block修饰的self造成的循环引用,并提出了使用__weak解决循环引用的策略。此外,还总结了Block面试中常见的问题,如Block的定义、循环引用的产生及消除方法、Block截获变量的特性等。
摘要由CSDN通过智能技术生成

什么是Block

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

__block修饰符

        一般情况下,对被截获变量进行赋值操作需要添加__block修饰符

对变量进行赋值时

        

Block 的几种形式

        分为全局Block( )、栈Block(_NSConcreteStackBlock)、堆
Block( )三种形式
        其中栈 Block 存储在栈(stack)区,堆 Block 存储在堆(heap)区,全局 Block 存储在已初始化数据(.data) 区

        不使用外部变量的 block 是全局 block
        使用外部变量并且未进行 copy 操作的 block 是栈 block

        对栈 block 进行 copy 操作,就是堆 block,而对全局 block 进行 copy,仍是全局 block

Block的copy操作

        问题1:由于block捕获的__block修饰的变量会去持有变量,那么如果用__block修饰self,且self 持有 block,并且 block 内部使用到__block 修饰的 self 时,就会造成多循环引用,即 self 持有 block, block 持有__block 变量,而__block 变量持有 self,造成内存泄漏。

        如果要解决这种循环引用,可以主动断开__block 变量对 self 的持有,即在 block 内部使用完 weakself 后,将其置为 nil,但这种方式有个问题,如果 block 一直不被调用,那么循环引用将一直存在。 所以,我们最好还是用__weak 来修饰 self

Block面试总结

问题1:什么是block?

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

问题2:为什么block会产生循环引用?

        1:如果当前block对当前对象的某一成员变量进行截获,这个block会对对应变量强引用,当block又由于当前对象对其有一个强引用,产生了一个自循环引用方式的问题。

        答:我们可以通过声明其为__weak变量进行循环引用的消除。

        2:如果定义了一个__block声明符的话那么也会产生循环引用但是要分场景。

        答:一种是在ARC下会产生循环引用,而在MRC下不会产生循环引用,在ARC下我们可以通过断环的方式接触对应循环引用,但是有一个弊端如果这个blcok一直得不到调用,这个循环引用是没办法解除的。

问题3:怎样理解Block截获变量的特性?

        对于基本数据类型局部变量是对其值进行截获。

        对于对象类型局部变量是对其进行强引用(连同其所有权修饰符共同进行截获)。

        对于静态局部变量对其指针进行截获。

        对于全局变量或者静态全局变量是不产生截获的。

 问题4:你都遇到过哪些循环引用?你是怎样解决的?

        Block所引起的循环引用是两方面的。

        一方面是block当中捕获的变量也是当前对象的成员变量,而这个block也是当前对象的成员变量,就会造成自循环引用,我们可以通过避免产生循环引用加__weak修饰符来避免这种循环引用

        第二方面__block也会产生循环引用,一种是在ARC下会产生循环引用,而在MRC下不会产生循环引用,在ARC下我们可以通过断环的方式接触对应循环引用,但是有一个弊端如果这个blcok一直得不到调用,这个循环引用是没办法解除的。

问题5:block为啥可以修改全局变量而局部变量修改需要加__blcok

block可以修改全局变量,是因为全局变量放在推区,局部变量在栈区,所以不能修改,加上__block之后,相当于加了个标识位,遇到__block就把内存由栈区放在推区。
 

        

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值