Block循环引用实例讲解

2017-02-27  本文已影响87人  9fda4b908fad

接上篇block实现原理探究,本篇为上篇的补充篇,如果有兴趣,可以看看上篇的内容(链接在这里),两篇内容的偏向有所不同,所以不用担心,会影响到本篇阅读.

block循环引用在日常开发过程中,是肯定会遇到的问题,除非你不使用block.但是可能有部分的小伙伴对这个问题没有深入的研究过,在这里,我希望抛砖引玉,希望能帮助到你.如果文中有不对的地方,欢迎指正.

下面开始进入正题:

下面以三种情形的方式分析,以下代码全部循环引用的全部代码

@interface TestViewController ()

@property (nonatomic,copy) void (^testBlock)();

@property (nonatomic,strong) Person *person;


@end

@implementation TestViewController

- (void)viewDidLoad {
    [super viewDidLoad];
   
    self.view.backgroundColor = [UIColor purpleColor];
    
    //情况一
   [self situationOne];
    
    //情况二
//    [self situationTwo];
    
    //情况二
//    [self situationThree];
}

- (void)situationOne
{
  
    self.testBlock = ^{
        
        NSLog(@"%@",self);
    };
    
    
}

- (void)situationTwo
{
    Person *p = [[Person alloc] init];

    p.block = ^{
        
        NSLog(@"%@",p);
    };
  
}

- (void)situationThree
{
    Person *p = [[Person alloc] init];
    
    p.block = ^{
        
        NSLog(@"%@",self);
    };
    
    self.person = p;

}


-(void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event
{
    [self dismissViewControllerAnimated:true completion:nil];
}


-(void)dealloc
{
    NSLog(@"%s:The CurrentViewController is Dealloc",__func__);
}

@end

另外一个Person文件

@interface Person : NSObject

@property (nonatomic,copy) void (^block)();

@end

解决上面两种情况循环引用的办法一样,就是让block里面引用外部的变量的形式变成弱引用,使引用环没有办法形成,以情形一为例,代码应该改为:

   __weak typeof(self) _self = self;
    
    self.testBlock = ^{
        
        NSLog(@"%@",_self);
    };
    Person *p = [[Person alloc] init];
    
    __weak typeof(self) _self = self;
    
    p.block = ^{
        
        NSLog(@"%@",_self);
    };
    
    self.person = p;

注: 以上代码在ARC环境下适用,如果在MRC的环境下,你需要将 __weak换成 __block

以上基本上就是开发中遇到比较多的循环引用的情况了,当然还要更加隐蔽的循环引用的情况存在,但是只要我们仔细一层一层的分析,还是能够发现的,多谢阅读.

上一篇下一篇

猜你喜欢

热点阅读