iOS - 重新打开应用程序时不显示NSUserDefaults Mutable Array

时间:2014-04-17 17:44:02

标签: ios objective-c nsmutablearray nsuserdefaults

这是我的mainAppDelegate.h

#import <UIKit/UIKit.h>

@interface mainAppDelegate : UIResponder <UIApplicationDelegate>

@property (strong, nonatomic) UIWindow *window;
@property NSMutableArray *toDoItems;

@end

和我的mainAppDelegate.m

#import "mainAppDelegate.h"

@implementation mainAppDelegate

- (void)applicationWillTerminate:(UIApplication *)application
{
    NSUserDefaults *defaults=[NSUserDefaults standardUserDefaults];
    [defaults setObject:self.toDoItems forKey:@"toDoItems"];
    [defaults synchronize];
}
@end

我有另一个文件XYZToDoListViewController.m,代码为:

#import "XYZToDoListViewController.h"
#import "XYZToDoItem.h"
#import "XYZAddItemViewController.h"

@interface XYZToDoListViewController ()
@property NSMutableArray *toDoItems;
@end

@implementation XYZToDoListViewController

- (IBAction)unwindToList:(UIStoryboardSegue *)segue
{
    XYZAddItemViewController *source = [segue sourceViewController];
    XYZToDoItem *item = source.toDoItem;
    if (item != nil) {
        [self.toDoItems addObject:item];
        [self.tableView reloadData];
    }
}

- (IBAction)clearData:(UIBarButtonItem *)sender;
{
    [self.toDoItems removeAllObjects];
    [self.tableView reloadData];
}

- (id)initWithStyle:(UITableViewStyle)style
{
self = [super initWithStyle:style];
if (self) {

}
return self;
}

   NSUserDefaults *defaults= [NSUserDefaults standardUserDefaults];
   if([[[defaults dictionaryRepresentation] allKeys] containsObject:@"toDoItems"]){
       NSLog(@"toDoItems found");
       self.toDoItems = [[NSMutableArray alloc]initWithArray:[[NSUserDefaults standardUserDefaults]objectForKey:@"toDoItems"]];
   } else {
      self.toDoItems = [[NSMutableArray alloc] init];
   }
   self.navigationController.view.backgroundColor =
   [UIColor colorWithPatternImage:[UIImage imageNamed:@"bg_full.png"]];
   self.tableView.backgroundColor = [UIColor clearColor];
   self.tableView.contentInset = UIEdgeInsetsMake(-35, 0, -35, 0);
   }
   @end

这至少是我认为相关的。我的基本框架是我this tutorial.

所遵循的内容

我做错了什么?当我将项目添加到我的待办事项列表中时,终止该应用程序,然后重新启动应用程序,我之前输入的数据不会显示。项目没有错误或警告,或崩溃。

6 个答案:

答案 0 :(得分:2)

我没有调用

applicationWillTerminate:,将userdfault synchronize代码放在其他地方。 顺便说一下,当你重新启动调试器时,该过程就被杀死了,而不是“终止”。

这就是为什么我通常在每次更改数据时调用synchronize,以确保在发生崩溃时保存数据,或者只是在我重新启动调试器时。

答案 1 :(得分:1)

[defaults setObject:self.toDoItems forKey:@"toDoItems"];


[[NSUserDefaults standardUserDefaults]objectForKey:@"loadItems"]

2不要使用相同的密钥。你设置@&#34; toDoItems&#34;并尝试获取@&#34; loadItems&#34;。

答案 2 :(得分:1)

您没有持久保存数据。现在,当您创建项目时,它将存在于内存中,但它永远不会写入磁盘,因此当应用程序终止时,将释放包含该项目的内存。您需要将项目写入磁盘,以便在应用程序终止后使用它们。您可以存档项目,也可以使用Core Data。不要使用NSUserDefaults进行用户设置。Here是一个存档教程,您可以在Apple开发者网站上找到核心数据指南。

答案 3 :(得分:1)

在一个完全不同的旁注,我想告诉你,你可以改变这个

if([[[defaults dictionaryRepresentation] allKeys] containsObject:@"toDoItems"]){ NSLog(@"toDoItems found"); self.toDoItems = [[NSMutableArray alloc]initWithArray:[[NSUserDefaults standardUserDefaults]objectForKey:@"toDoItems"]]; } else { self.toDoItems = [[NSMutableArray alloc] init]; }

到那个

self.toDoItems = [[NSMutableArray alloc]initWithArray:[[NSUserDefaults standardUserDefaults]objectForKey:@"toDoItems"]];

因为如果你试图获得一个没有从用户默认值(或任何字典)设置的对象,你将得到零。如果你使用nil数组初始化你的可变数组,你将拥有一个有效但空的可变数组。

因为它不适合作为评论我把它写成答案,虽然它当然与你原来的问题无关

答案 4 :(得分:0)

我想你不会在mainAppDelegate类上保存列表。因此,您需要将数据保存在正在形成列表的类中,并删除mainAppDelegate的调用。也许您在应用终止时保存零值。

NSUserDefaults *defaults=[NSUserDefaults standardUserDefaults];
[defaults setObject:self.toDoItems forKey:@"toDoItems"];
[defaults synchronize];

稍后您需要使用相同的键 @&#34; toDoItems&#34; 来调用它。

答案 5 :(得分:0)

您尝试模拟被调用的applicationWillTerminate时会非常困难。

我建议您在数据发生变化时(首选)保存数据,或至少保存一些可预测的数据applicationWillEnterForeground:applicationWillResignActive:

- (void) applicationWillResignActive:(UIApplication *)application
{
    NSUserDefaults *defaults=[NSUserDefaults standardUserDefaults];
    [defaults setObject:self.toDoItems forKey:@"toDoItems"];
    [defaults synchronize];
}

正如Emilie Lessard所指出的那样,必须使用相同的密钥来获取正确的数据。

[[NSUserDefaults standardUserDefaults]objectForKey:@"toDoItems"];