2012-03-15 99 views
0
- (void)viewDidLoad 
{ 
    [super viewDidLoad]; 
    // Do any additional setup after loading the view, typically from a nib. 

    NSUserDefaults *somet = [NSUserDefaults standardUserDefaults]; 

    NSMutableArray *anArr = [somet objectForKey:@"somedata"] ; 

    NSLog(@"anArr::: %@",anArr); 

} 

-(IBAction)addsomething:(id)sender{ 

    if (something == nil) { 
     array = [[NSMutableArray alloc] init]; 
    } 
    NSLog(@"textfieldvalue::: %@", textfield.text); 

    [array addObject:textfield.text]; 

    NSUserDefaults *something = [NSUserDefaults standardUserDefaults]; 

    [something setObject:array forKey:@"somedata"]; 

    array = [something objectForKey:@"somedata"]; 

    NSLog(@"array:: %@", array); 

} 

使用上面的代码,我试图在NSMutableArray中动态保存数据,然后将它保存在NSUserDefaults中。但在检索它时,我得到(null)。即使数据没有被保存在数组中。NSMutableArray和NSUserdefaults问题iPhone

如何正确保存数据?

EDITED: 

2012-03-15 15:17:18.431 check[2686:40b] anArr::: (null) 
2012-03-15 15:17:30.160 check[2686:40b] textfieldvalue::: a 
2012-03-15 15:17:30.162 check[2686:40b] array::: (null) 
+0

你在哪里初始化'array'?此外,'objectForKey:'不会返回一个可变数组实例('NSMutableArray')。 – 2012-03-15 08:05:14

+0

请检查我编辑了我的问题 – 2012-03-15 08:07:07

+0

现在它更令人困惑。为什么要检查'无'的东西?它还没有初始化。 – 2012-03-15 08:10:34

回答

3

没有违法,但你的代码是一堆废话。

  1. 变量名为something没有用。期。
  2. 你有一个变量在你的本地方法中名为something。你有一个变量,它是你类的一部分。 “局部变量隐藏实例变量”警告是有原因的!
    也许这就是你所有的问题来自哪里。我认为你不太了解局部变量的概念。如果是这种情况,你应该阅读更多关于基本Objective-C的东西。
  3. 你检查是否有零,然后你不改变的东西,但你分配一个数组。这两者没有任何关系。不要写这样的代码。

我固定它给你:

- (void)viewDidLoad 
{ 
    [super viewDidLoad]; 
    NSUserDefaults *userDefaults = [NSUserDefaults standardUserDefaults]; 
    NSArray *anArr = [userDefaults objectForKey:@"somedata"]; 
    NSLog(@"anArr::: %@",anArr); 
} 

-(IBAction)addsomething:(id)sender{ 
    NSMutableArray *array = [[NSMutableArray alloc] init]; 
    NSLog(@"textfieldvalue::: %@", textfield.text); 
    [array addObject:textfield.text]; 
    NSUserDefaults *userDefaults = [NSUserDefaults standardUserDefaults]; 
    [userDefaults setObject:array forKey:@"somedata"]; 
    array = [userDefaults objectForKey:@"somedata"]; 

    // synchronize is only needed while debugging (when you use the stop button in Xcode) 
    // you don't need this in production code. remove it for release 
    [userDefaults synchronize]; 

    NSLog(@"array:: %@", array); 
} 

然而,很可能要对象保存到你userDefaults得到了数组。这不适用于局部变量!

你会使用这样的东西。但不要复制这些逐字。尝试了解它,并阅读更多关于局部变量。

NSUserDefaults *userDefaults = [NSUserDefaults standardUserDefaults]; 
array = [[userDefaults objectForKey:@"somedata"] mutableCopy]; 
if (!array) { 
    // create array if it doesn't exist in NSUserDefaults 
    array = [[NSMutableArray alloc] init]; 
} 
NSLog(@"array in viewDidLoad: %@",array); 



NSLog(@"textfieldvalue::: %@", textField.text); 
[array addObject: textField.text]; 
NSUserDefaults *userDefaults = [NSUserDefaults standardUserDefaults]; 
[userDefaults setObject:array forKey:@"somedata"]; 

// synchronize is only needed while debugging (when you use the stop button in Xcode) 
// you don't need this in production code. remove it for release 
[userDefaults synchronize]; 
+0

非常感谢你,已经试过你的代码,但我得到这个结果 2012-03-15 15:51:36.832 check [3025:40b] textfieldvalue ::: a 2012-03-15 15:51:36.845 check [3025:40b] array ::(a) 2012-03-15 15:51:44.712 check [3025:40b] textfieldvalue ::: b 2012-03-15 15:51:44.738 check [3025:40b ] array ::(b) – 2012-03-15 10:54:03

+0

它将用新的元素替换之前的元素,而不是添加新元素。就像插入“a”那么数组是array ::(a)然后在输入b之后,数组应该是数组::(a,b),但是它给出array ::(b) – 2012-03-15 10:56:28

+2

我的答案的代码块,并尝试了解它的功能。它应该做到这一点。请记住:array是一个实例变量,而不是局部变量。 – 2012-03-15 10:59:36

3

尝试下面的代码可能会帮助ü...

- (void)viewDidLoad 
{ 
[super viewDidLoad]; 
// Do any additional setup after loading the view, typically from a nib. 

NSUserDefaults *somet = [NSUserDefaults standardUserDefaults]; 

NSMutableArray *anArr = [[NSMutableArray alloc] init]; 
anArr = [somet objectForKey:@"somedata"] ; 
[somet synchronize]; 

NSLog(@"anArr::: %@",anArr); 

} 

-(IBAction)addsomething:(id)sender{ 

NSLog(@"textfieldvalue::: %@", textfield.text); 
//Here u have to check array is in memory allocate or not 
[array addObject:textfield.text]; 

NSUserDefaults *something = [NSUserDefaults standardUserDefaults]; 

[something setObject:array forKey:@"somedata"]; 
[something synchronize]; 

array = [something objectForKey:@"somedata"]; 

NSLog(@"array:: %@", array); 

} 
+0

你正在分配一个nsmutable数组,然后分配一个对象,没有意义 – 2012-03-15 08:18:44

+0

仍然是相同的结果,在NSLog(@“array ::%@”,array);它说(nul) – 2012-03-15 08:22:08

+0

问题现在被编辑 – 2012-03-15 10:20:57

2

您需要在您setObject:forKey调用[[NSUserDefaults standardUserDefaults] synchronize];

[something setObject:array forKey:@"somedata"]; 
[something synchronize]; 
+0

试过了,但仍然是数组null::( – 2012-03-15 08:42:16

0

加入这一行,

[something synchronize] 

检索数据之前。

+0

抱歉,你现在是我关于同步恋物癖的咆哮的目标,'同步'通常是没有必要的!你强制NSUserDefaults将整个设置文件写入文件系统,Apple实现了NSUserDefaults,以便它知道什么时候需要写入它的设置(例如,当应用程序进入后台或退出时),'synchronize'在调试时可能没有问题,当你偶尔用Xcode停止按钮强制停止应用程序时,但是经验表明,这样的代码从未被删除,因为它“有效” – 2012-03-15 10:55:59

+0

**结论:不要在每次调用后放置一个[userDefaults synchronize]这改变了NSUserDefaults。** NSUserDefaults是聪明的!它被缓存在内存中,并且只在必要时写入磁盘。 – 2012-03-15 10:56:54

+0

@MatthiasBauch。Very Insight首先感谢您的评论。我解决了同步问题,但没有意识到它很重。我会牢记这一点。 – Vignesh 2012-03-15 11:47:57

0

试试这个当您保存价值为NSUserDefaults

- (void)savingObject:(NSString *)keyName data:(id)val 
{ 
    NSData *dataVal = [NSKeyedArchiver archivedDataWithRootObject:val]; 
    [defaults setObject:dataVal forKey:keyName]; 
    [defaults synchronize]; 
} 

,然后当你想要得到的是使用这种

- (id)gettingObject:(NSString *)keyName 
{ 
    NSData *data = [[NSUserDefaults standardUserDefaults] objectForKey:keyName]; 
    return [NSKeyedUnarchiver unarchiveObjectWithData:data]; 
} 

我认为这可以帮助你

+0

不需要为保存NSString(如textField.text)这样做。 NSStrings是一个plist风格的属性,可以直接保存到NSUserDefaults – 2012-03-15 10:50:36

+0

是的,我知道,但他正在'NSUserDefaults'添加'NSMutableArray',所以建议他这样做。 – hchouhan02 2012-03-15 12:25:21