UIViewController 关闭时不接收 dealloc 或 viewDidUnload

Posted

技术标签:

【中文标题】UIViewController 关闭时不接收 dealloc 或 viewDidUnload【英文标题】:UIViewController does not receive dealloc or viewDidUnload when dismissed 【发布时间】:2012-02-10 15:35:47 【问题描述】:

更新:我在调试中犯了一个错误 - 这个问题无关紧要 - 请参阅下面的评论。

注意:我正在使用自动引用计数

当我的应用程序启动时 - 我在 UINavigationControllerpresentViewController:animated:completion 中显示了一个视图控制器。该视图控制器将第二个视图控制器加载到导航堆栈上。第二个视图控制器使用[self.presentingViewController dismissViewControllerAnimated:YES completion:nil] 关闭自己。我的问题是,在第一个视图控制器中既没有调用 dealloc 也没有调用 viewDidUnload。但是,使用工具,我可以看到一旦呈现的视图控制器被解除,视图控制器就不再被分配。呈现第一个视图控制器的代码是

- (void)viewDidAppear:(BOOL)animated                                                                                                                                                                                                         
                                                                                                                                                                                                                                            
    [super viewDidAppear:animated];                                                                                                                                                                                                          

    //  check if our context has any accounts                                                                                                                                                                                                
    if( [self.accounts count] == 0 )                                                                                                                                                                                    
                                                                                                                                                                                                                                            
        //  Display the Add Account View Controller                                                                                                                                                                                          
        MySettingsViewController *settingsVC = [[MySettingsViewController alloc] initWithNibName:@"MySettingsViewController" bundle:nil];                                                                                                 
        settingsVC.appContext = self.appContext;                                                                                                                                                                                             

        UINavigationController *navVC = [[UINavigationController alloc] initWithRootViewController:settingsVC];                                                                                                                              
        navVC.modalTransitionStyle = UIModalTransitionStyleCrossDissolve;                                                                                                                                                                    

        if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPhone)                                                                                                                                                      
                                                                                                                                                                                                                                            
            //  Display the Add Account View Controller                                                                                                                                                                                      
                                                                                                                                                                                                                                            
        else                                                                                                                                                                                                                                 
                                                                                                                                                                                                                                            
            navVC.modalPresentationStyle = UIModalPresentationFormSheet;                                                                                                                                                                     
                                                                                                                                                                                                                                            

       [self presentViewController:navVC animated:YES completion:nil];                                                                                                                                                                       
                                                                                                                                                                                                                                            
            

所以,我没有任何应该保留的对 settingsVC 的引用,但我不知道为什么我的 dealloc 没有被调用。任何帮助都会很棒。

【问题讨论】:

我是个白痴。我将我正在测试的 dealloc 方法放在错误的视图控制器中。所以我的 dealloc 被调用,这是有道理的。 【参考方案1】:

他们没有被调用,因为你没有正确地释放你的视图控制器。

您将settingsVCnavVC 分配给alloc,从而获得对两者的引用,您必须稍后发布而您没有这样做。

你可以这样做:

- (void)viewDidAppear:(BOOL)animated                                                                                                                                                                                                         
                                                                                                                                                                                                                                            
    [super viewDidAppear:animated];                                                                                                                                                                                                          

    //  check if our context has any accounts                                                                                                                                                                                                
    if( [self.accounts count] == 0 )                                                                                                                                                                                    
                                                                                                                                                                                                                                            
        //  Display the Add Account View Controller                                                                                                                                                                                          
        MySettingsViewController *settingsVC = [[MySettingsViewController alloc] initWithNibName:@"MySettingsViewController" bundle:nil];                                                                                                 
        settingsVC.appContext = self.appContext;                                                                                                                                                                                             

        UINavigationController *navVC = [[UINavigationController alloc] initWithRootViewController:settingsVC];
        navVC.modalTransitionStyle = UIModalTransitionStyleCrossDissolve;                                                                                                                                                                    

        // At this points, "settingsVC" is additionally retained by the navigation controller,
        // so we can release it now.
        [settingsVC release];

        if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPhone)                                                                                                                                                      
                                                                                                                                                                                                                                            
            //  Display the Add Account View Controller                                                                                                                                                                                      
                                                                                                                                                                                                                                            
        else                                                                                                                                                                                                                                 
                                                                                                                                                                                                                                            
            navVC.modalPresentationStyle = UIModalPresentationFormSheet;                                                                                                                                                                     
                                                                                                                                                                                                                                            

        [self presentViewController:navVC animated:YES completion:nil];

        // At this point "navVC" is retained by UIKit, so we can release it as well.
        [navVC release];
                                                                                                                                                                                                                                            
           

另一种选择是立即使用autorelease

【讨论】:

我正在使用自动引用计数 - 仍然是这种情况吗?对此感到抱歉-我以为我将其包含在我的问题中。我已对其进行了更新以反映这一点。 当然 ARC 在这里有所作为......好吧,在那种情况下,我不知道发生了什么,抱歉。 你能告诉我我的假设是否应该调用 dealloc 或 viewDidUnload - 意思是我对内存管理和 UIViewControllers 的理解是否正确? 是的,一旦相应的视图控制器被解除,两者都应该被调用。

以上是关于UIViewController 关闭时不接收 dealloc 或 viewDidUnload的主要内容,如果未能解决你的问题,请参考以下文章

UITableView,离屏,滑入屏幕时不接收触摸事件

UIViewController 在 dealloc 时不释放子视图(使用 ARC)

如何使 UIViewController 工具栏出现? [关闭]

活动开始但在屏幕关闭或锁定时不可见

Xamarin.Android FCM 通知在应用程序关闭/后台时不显示在 HUD 中

手机蓝牙与手机蓝牙连接时不弹出配对码对话框