如果视图控制器由于内存警告而被卸载,如何恢复状态?

Posted

技术标签:

【中文标题】如果视图控制器由于内存警告而被卸载,如何恢复状态?【英文标题】:How do I restore state if a view controller gets unloaded due to a memory warning? 【发布时间】:2012-08-07 08:17:55 【问题描述】:

我有一个视图控制器,它获取由它推送的视图控制器设置的属性。

基本上,我有类似的东西

- (void)doStuff 
    [self performSegueWithIdentifier:@"segueToThing" sender:self];


- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender 
    if([[segue identifier] isEqualToString:@"segueToThing"])
        [(ThingViewController *)[segue destinationViewController] setImportantData:[self importantData]];

问题是,如果我推ThingViewController,然后在其上推另一个视图控制器,然后发出内存警告,我的ThingViewController 将被卸载以释放内存。然后我弹出第三个视图控制器,我的ThingViewController 再次加载,但我在segue 中设置的importantData 属性现在是nil,因为segue 没有再次被触发。

我该怎么办?我是否应该将所有状态存储在某个地方...?

【问题讨论】:

【参考方案1】:

如果您不想释放该内存,请不要在内存警告或 viewDidUnload 中释放它。

如果需要释放内存,把数据持久化,等VC回来后重新加载。

【讨论】:

我试着不在我的 viewDidUnload 中释放它,但是当内存警告发生时,VC 似乎被完全拆除并重建并失去了它的所有属性。您能否详细说明我将如何保留这些数据?我是否必须做一些愚蠢的事情,比如将其放入静态变量或其他东西中? 您应该发布一些代码,即与视图控制器生命周期相关的任何内容(viewDidLoad/Unload 初始化程序、didReceiveMemoryWarning 等)以及您对正在消失的重要事物的管理。【参考方案2】:

也许将重要数据存储在AppDelegate中?在您的 AppDelegate.h 文件中声明一个 NSData 对象或任何需要保存的对象。然后在prepareForSegue 期间,您会得到对AppDelegate 的引用,如下所示:

AppDelegate *appDel = [[UIApplication sharedApplication] delegate];

然后使用您在 AppDelegate 中保存的变量保存您的对象。然后当第二个视图再次加载时,只需再次调用 AppDelegate 并使用来自 App Delegate 的数据。希望这能有所帮助。如果您需要更多帮助或者我不清楚,请告诉我。

【讨论】:

我考虑过,但我希望有更好的方法。我的意思是,如果提供prepareForSegue: 是为了完成我正在做的事情,我不明白为什么默认的UIViewController 内存警告行为是丢弃该数据。 我明白了。为什么要发出低内存警告?也许你可以不这样做。 我只是模拟内存警告来测试。我注意到当应用程序运行时,它会在使用UIWebView 时收到很多内存警告。 不,不要那样做。看看那个类的名字...... AppDelegate。它用于处理来自 UIApplication 的委托方法。它不是设计垃圾的倾倒场。

以上是关于如果视图控制器由于内存警告而被卸载,如何恢复状态?的主要内容,如果未能解决你的问题,请参考以下文章

卸载xampp后如何在phpmyadmin中恢复数据库

视图控制器MVC屏幕旋转内存警告

为啥我的视图在内存不足警告时消失了?

iOS - 内存警告会卸载 View Controller 并使应用程序无响应

每次都恢复状态?

在模态视图控制器上模拟内存警告清除前一个控制器的内容