如何在iOS中使用NSUserDafaults保存和检索NSObject类
您好我想保存和检索使用NSUserDefaults
NSObject
类为我写下面的代码,但我得到像下面的exception
由于未捕获exception“
NSInvalidArgumentException
”而终止应用程序,原因:“尝试为键DATA插入非属性列表对象”
为了节省: –
SavingBean*savingbean = [[SavingBean alloc]init]; [savingbean savingData:userName.text :passWord.text]; NSUserDefaults * defaults = [[NSUserDefaults alloc]init]; [defaults setObject:savingbean forKey:@"DATA"];
检索: –
defaults = [[NSUserDefaults alloc]init]; savingbean = [defaults objectForKey:@"DATA"]; NSLog(@"Username is===>%@",savingbean.userName); NSLog(@"Password is===>%@",savingbean.passWord);
ModelClas: –
.h文件: –
#import <Foundation/Foundation.h> @interface SavingBean : NSObject{ NSString *userName; NSString *passWord; } @property(nonatomic, retain) NSString *userName; @property(nonatomic, retain) NSString *passWord; -(void)savingData :(NSString*)userName :(NSString*)password; @end
.m文件: –
#import "SavingBean.h" @implementation SavingBean @synthesize userName,passWord; -(void)savingData :(NSString*)username :(NSString*)password{ userName = username; passWord = password; } @end
你可以像这样设置对象:
NSUserDefaults *currentDefaults = [NSUserDefaults standardUserDefaults]; NSData *data = [NSKeyedArchiver archivedDataWithRootObject:savingbean]; [currentDefaults setObject:data forKey:@"DATA"]; [currentDefaults synchronize];
并获得像这样的对象:
NSData *data = [currentDefaults objectForKey:@"DATA"]; SavingBean *token = [NSKeyedUnarchiver unarchiveObjectWithData:data];
对于Custom类,你必须在你的bean类中编辑这个方法:
- (void)encodeWithCoder:(NSCoder *)encoder { [encoder encodeObject:self.userName==nil?@"":self.userName forKey: @"userName"]; [encoder encodeObject:self.passWord==nil?@"":self.passWord forKey: @"passWord"]; } -(id)initWithCoder:(NSCoder *)decoder { self = [super init]; if(self) { self.userName = [decoder decodeObjectForKey: @"userName"]; self.passWord = [decoder decodeObjectForKey: @"passWord"]; } return self; }
这里是大多数投票相似的答案。 你也可以从那里得到好东西。
您也可以使用JSON加速器来创buildbean类。 这是非常简单而强大的工具。
从Jayesh Thanki的良好答案我试着从这个问题的样本。我跟着你的编码。首先,我试着直接保存和检索没有编码器和解码器的方法。
保存
NSUserDefaults *currentDefaults = [NSUserDefaults standardUserDefaults]; NSData *data = [NSKeyedArchiver archivedDataWithRootObject:savingbean]; [currentDefaults setObject:data forKey:@"DATA"]; [currentDefaults synchronize];
用于检索
NSData *data = [currentDefaults objectForKey:@"DATA"]; savingbean = [NSKeyedUnarchiver unarchiveObjectWithData:data];
现在它显示错误
[SavingBean encodeWithCoder:]:无法识别的select器发送到实例0x7fc65940fc40
由于未捕获的exception“NSInvalidArgumentException”而终止应用程序,原因:' – [SavingBean encodeWithCoder:]:无法识别的select器发送到实例0x7fc65940fc40'
然后我search了大部分答案
NSCoding协议声明了一个类必须实现的两个方法,以便该类的实例可以被编码和解码。 此function为归档(其中对象和其他结构存储在磁盘上)和分发(将对象复制到不同的地址空间)提供了基础。
encodeWithCoder
encodeWithCoder:指示对象将其实例variables编码到所提供的编码器; 一个对象可以多次接收这个方法。
的initWithCoder
initWithCoder:指示对象从提供的编码器中的数据初始化自己; 因此,它取代了其他的初始化方法,每个对象只发送一次。
然后我明白,我们必须先在NSObject类中实现encodeWithCoder和inintWithCoder,然后才能保存和检索数据。
– > 编码器是一个归档器对象
– > 解码器是一个unarchiver对象
现在,首先我们必须在SavingBean.m中实现encodeWithCoder和initWithCoder
- (void)encodeWithCoder:(NSCoder *)encoder { //Encode properties, other class variables, etc [encoder encodeObject:@"AbhiRam" forKey:@"username"]; [encoder encodeObject:@"Test@123" forKey:@"password"]; } - (id)initWithCoder:(NSCoder *)decoder { if((self = [super init])) { //decode properties, other class vars userName = [decoder decodeObjectForKey:@"username"]; passWord = [decoder decodeObjectForKey:@"password"]; } return self; }
然后在ViewController.m中
保存
SavingBean *savingbean = [[SavingBean alloc]init]; NSUserDefaults *currentDefaults = [NSUserDefaults standardUserDefaults]; NSData *data = [NSKeyedArchiver archivedDataWithRootObject:savingbean]; [currentDefaults setObject:data forKey:@"DATA"]; [currentDefaults synchronize];
用于检索
NSData *data = [currentDefaults objectForKey:@"DATA"]; savingbean = [NSKeyedUnarchiver unarchiveObjectWithData:data];
现在,当我运行该应用程序,它不显示任何错误。它现在工作正常。
为什么我在这里给这些东西是如果有人看到和尝试这个答案,在某些情况下,他们可以得到上述的错误。所以如果他们喜欢这个问题的两个答案,他们可以很容易地理解和得到解决scheme很简单。
encodeWithCoder和NSWoding的initWithCoder
- MKPolyline / MKPolylineRenderer改变颜色而不删除它
- 我应该使用什么,而不是在iOS5.1中弃用的UISegmentedControlStyleBezeled?
- 在ViewControllers的iOS 7中使用JavaScriptCore从JavaScript触发目标C方法
- Swift + CoreData:无法在NSManagedObject子类上设置Bool – Bug?
- 检查应用程序是否构建为发布
- Azure DocumentDB通过Obj-c查询REST API时发生间歇性401错误
- 在实现文件中声明接口(Objective-C)
- Facebook SDK的FBSDKShareDialog不适用于iOS9?
- Swift中的callback函数语法