• 问题:viewController不会调用dealloc()不会销毁


    问题

    在调试程序时,我从ViewController A push进 ViewController B,在从B back时发现程序不会执行B里面的dealloc(),很诡异的问题,因为按理说此时点击back是执行pop操作的,是会执行dealloc()函数的,但经调试发现确实没有执行。所以viewController也就不会销毁.

    原因

    The dealloc method was not being called if any of the references held by a viewcontroller were still in memory. 也就是说,我当前View B 内存中计数器不为0,还有一些内容的引用计数不为0, 所以造成了 controller 不能及时释放.

    解决

    我发现在我的代码里有一个倒计时的计时器的功能, 是通过 NSTimer实现的, 
    在调用的时候对 target:self 进行了retain, 这时候你pop回上一级,self的引用计数还剩1,所以肯定不会dealloc. 当其倒计时结束后, 我有一个[timer invalidate]的方法, 这个时候才会调用 dealloc.  
    所以我的解决办法是在viewWillDisappear: 方法中执行[timer invalidate];这样,self view计数器为0,当前view就会自动调用delloc()。

    总结

    其实这个问题, 就跟循环引用的问题是类似的, 都是由于内存考虑不周全管理不当造成的. 但是很多时候都会出现, 尤其是在 NSTimer , block , delegate, 使用的时候, 很容易造成当前页面不能及时销毁, 从而导致内存泄露. timer 一定要及时invalidate, block 要用 copy修饰而且还有防止析构和 block块内的循环引用, delegate 要用assign 修饰. 等等都需要好好注意.

    controller 不能释放,不走dealloc方法的4种可能

    第一种: controller中使用了计时器 NSTimer 使用后没有销毁 导致循环引用

    self.playerTimer = [NSTimerscheduledTimerWithTimeInterval:1target:selfselector:@selector(playProgressAction)userInfo:nilrepeats:YES];

    使用后记得销毁

     
    
       [_playerTimerinvalidate];
    
        _playerTimer =nil;

    第二种:协议delegate 应该使用weak修饰,否则会引起循环引用 不能释放内存

    @property (nonatomic,weak)id<huifuDelegate>huifudelegate;

    第三种:使用到block的地方,,block回调中不能直接使用self 否则可能引起循环引用。

     
    
       __weaktypeof(self) weakSelf =self;
    
        _audioStream.onCompletion=^(){
    
            [weakSelf nextButtonAction];
    
        };

    第四种:

    对于前三种 大家可能都知道,,我发现一个会导致controller不能释放的情况,,很诡异,,pop后不走dealloc  再push进来会走一次dealloc..这种情况是我接手的工程中出现的问题,,不仅不能释放 ,,如果这个controller中有音频 视频的录制,,应用退入后台会出现麦克风后台使用的提示。。如果有使用AirPlay 播放音频 ,,也会对AirPlay的时间显示产生干扰。。当然这都是没释放内存引起的。。。。。。。

    具体的情况如下,

    有ViewController和ceshiViewController   ViewController要push到ceshiViewController

    #import "ViewController.h"
    
    #import "ceshiViewController.h"
    
     
    
    @interfaceViewController (){
    
        ceshiViewController *ceshiVC;// 使用实例变量声明的时候,,我是不怎么这样写
    
    }
    
     
    - (void)action{
    
        ceshiVC =  [[ceshiViewControlleralloc]init];///这样写就出问题了
    
        [self.navigationControllerpushViewController:ceshiVCanimated:YES];
    
    }
    
    /////////////==============///////////////////
    
     
    
    #import "ceshiViewController.h"
    
     
    
    @interfaceceshiViewController ()
    
     
    
    @end
    
     
    
    @implementation ceshiViewController
    
    - (void)dealloc{
    
        NSLog(@"---释放");
    
     
    
    }

    controller 返回后不会释放。。。。。。。。

    5.。。。。项目中遇到的不走dealloc情况

     
    
    @interface TopicDetailViewController (){
    
     
    
        NSInteger videoType;
    
    }
    
     
    
    - (void)addFooterData{
    
      __weak TopicDetailViewController *weakself = self;
    
        self.TopicDetailTableView.mj_footer = [MJRefreshAutoNormalFooter footerWithRefreshingBlock:^{
    
            [weakself loadDataWithtype:videoType];  
    
            /// 在这里使用videoType后 不走dealloc 换成属性创建,,使用weakself.videoType 可解决
    
        }];
    
    }
  • 相关阅读:
    CF 980D Perfect Groups(数论)
    CF 983B XOR-pyramid(区间dp,异或)
    CF 984C Finite or not? (数论)
    CF 979D Kuro and GCD and XOR and SUM(异或 Trie)
    (可能)常用打比赛网站
    排序工作量之新任务(SHOI2001)
    【图楼】长期图楼~~不定期更新
    【题解】SHOI2014概率充电器
    【题解】NOIP2015推销员
    [NOI2015][bzoj4197] 寿司晚宴 [状压dp+质因数]
  • 原文地址:https://www.cnblogs.com/henusyj-1314/p/8533198.html
Copyright © 2020-2023  润新知