在iOS中保存/序列化自定义对象的正确方法

时间:2011-03-24 01:46:33

标签: iphone ios

我有一个自定义对象,一个UIImageView子类,它有几个gestureRecognizer个对象。

如果我在NSMutableArray中存储了许多这些对象,那么如何将这个对象数组保存到磁盘中,以便在用户再次运行应用程序时加载它?

我想从磁盘加载数组并使用这些对象。

4 个答案:

答案 0 :(得分:118)

我对类似内容的实现如下并且完美运行:

自定义对象(设置)应实现协议NSCoding:

-(void)encodeWithCoder:(NSCoder *)encoder{
    [encoder encodeObject:self.difficulty forKey:@"difficulty"];
    [encoder encodeObject:self.language forKey:@"language"];
    [encoder encodeObject:self.category forKey:@"category"];
    [encoder encodeObject:self.playerType forKey:@"playerType"];
}

- (id)initWithCoder:(NSCoder *)decoder {
    if (self = [super init]) {
        self.difficulty = [decoder decodeObjectForKey:@"difficulty"];
        self.language = [decoder decodeObjectForKey:@"language"];
        self.category = [decoder decodeObjectForKey:@"category"];
        self.playerType = [decoder decodeObjectForKey:@"playerType"];
    }
    return self;
}

以下代码将自定义对象写入文件(set.txt),然后将其还原到数组myArray:

NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *appFile = [documentsDirectory stringByAppendingPathComponent:@"set.txt"];

NSMutableArray *myObject=[NSMutableArray array];
[myObject addObject:self.settings];    

[NSKeyedArchiver archiveRootObject:myObject toFile:appFile]; 

NSMutableArray* myArray = [NSKeyedUnarchiver unarchiveObjectWithFile:appFile]; 

答案 1 :(得分:35)

//store the array
[NSKeyedArchiver archiveRootObject:myArray toFile:@"someFile"];

//load the array
NSMutableArray* myArray = [NSKeyedUnarchiver unarchiveObjectWithFile:@"someFile"];

Official References

请注意,当数组包含自定义对象类型时,必须确保您的类型符合NSCoding Protocol之前的效果。

答案 2 :(得分:6)

此博客文章介绍了如何使用NSKeyedArchiver将一系列自定义对象存储到磁盘,并使用NSKeyedUnarchiver将其读回:

http://www.cocoabuilder.com/archive/cocoa/240775-saving-nsarray-of-custom-objects.html

Apple也有一个非常有用的指南,Archives and Serializations Programming Guide

答案 3 :(得分:2)

如果有人需要,我想与Kostas解决方案分享我的改进。

  1. 类名可用于生成存储对象的文本文件名。
  2. 在viewWillDisappear方法中保存视图控制器的对象并在viewDidLoad方法中恢复它们是一个很好的解决方案。
  3. 文件名应以单独的方法生成,以避免重复的代码。
  4. 恢复对象后,应检查它是否为零。

  5. - (void)viewDidLoad
    {
      [super viewDidLoad];
    
      // Restoring form object from the file
      NSString *formFilePath = [self formFilePath];
      RRCreateResumeForm *form = [NSKeyedUnarchiver unarchiveObjectWithFile:formFilePath];
      if (form != nil) {
        self.formController.form = form;
      }
    }
    
    
    - (void)viewWillDisappear:(BOOL)animated
    {
      [super viewWillDisappear:animated];
    
      // Saving the form object to the file
      NSString *formFilePath = [self formFilePath];
      [NSKeyedArchiver archiveRootObject:self.formController.form toFile:formFilePath];
    }
    
    
    // Returns a file path to the file with stored form data for form controller
    - (NSString *)formFilePath
    {
      NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
      NSString *documentsDirectory = [paths objectAtIndex:0];
      NSString *formClassName = NSStringFromClass( [self.formController.form class] );
      NSString *formFileName = [NSString stringWithFormat:@"%@.txt", formClassName];
      NSString *formFilePath = [documentsDirectory stringByAppendingPathComponent:formFileName];
    
      return formFilePath;
    }