iOS 数据持久化二-对象归档

来源:互联网 发布:胸卡制作软件 编辑:程序博客网 时间:2024/05/03 13:58

iOS中有五种持久化数据的方式:属性列表、对象归档、NSUserDefaults、SQLite3和Core Data。

本文介绍对象归档来持久化数据。归档的作用就是将对象以文件的形式保存到磁盘中,以使得数据序列化和持久化。

使用归档的时候读取该文件保存路径来读取文件的内容,归档的文件是进行过保密处理的,在磁盘上是无法查看文件的内容的,这也是和属性列表的区别:属性列表是明文,可以直接从磁盘查看其内容。

使用归档需要使用NSCoding协议中的代理两个方法

[objc] view plaincopy在CODE上查看代码片派生到我的代码片
  1. @protocol NSCoding  
  2.   
  3. - (void)encodeWithCoder:(NSCoder *)aCoder;  
  4. - (id)initWithCoder:(NSCoder *)aDecoder;  
  5.   
  6. @end  


自定义类进行归档:
[objc] view plaincopy在CODE上查看代码片派生到我的代码片
  1. //  
  2. //  ScoreCard.h  
  3. //  ArchiverDemo  
  4. //  
  5. //  Created by swplzj on 13-11-19.  
  6. //  Copyright (c) 2013年 swplzj. All rights reserved.  
  7. //  
  8.   
  9. #import <Foundation/Foundation.h>  
  10. //遵循NSCoding协议  
  11. @interface ScoreCard : NSObject<NSCoding>  
  12. {  
  13.     NSString *_bestTime;  
  14.     NSMutableArray *_allTimes;  
  15. }  
  16.   
  17. @property (copynonatomicNSString *bestTime;  
  18. @property (copyNSMutableArray *allTimes;  
  19.   
  20. @end  

[objc] view plaincopy在CODE上查看代码片派生到我的代码片
  1. //  
  2. //  ScoreCard.m  
  3. //  ArchiverDemo  
  4. //  
  5. //  Created by swplzj on 13-11-19.  
  6. //  Copyright (c) 2013年 swplzj. All rights reserved.  
  7. //  
  8.   
  9. #import "ScoreCard.h"  
  10.   
  11. @implementation ScoreCard  
  12.   
  13. @synthesize bestTime = _bestTime;  
  14. @synthesize allTimes = _allTimes;  
  15.   
  16. - (void)dealloc  
  17. {  
  18.     [_bestTime release];  
  19.     [_allTimes release];  
  20.       
  21.     [super dealloc];  
  22. }  
  23.   
  24. - (id)init  
  25. {  
  26.     if (self = [super init]) {  
  27.         _bestTime = [[NSString alloc] init];  
  28.         _allTimes = [[NSMutableArray alloc] init];  
  29.     }  
  30.     return self;  
  31. }  
  32.   
  33. //解码方法  
  34. - (id)initWithCoder:(NSCoder *)aDecoder  
  35. {  
  36.     if (self = [super init]) {  
  37.         _bestTime = [[aDecoder decodeObjectForKey:@"bestTime"] retain];  
  38.         _allTimes = [[aDecoder decodeObjectForKey:@"allTimes"] retain];  
  39.     }  
  40.     return self;  
  41. }  
  42.   
  43. //编码方法  
  44. - (void)encodeWithCoder:(NSCoder *)aCoder  
  45. {  
  46.     [aCoder encodeObject:_bestTime forKey:@"bestTime"];  
  47.     [aCoder encodeObject:_allTimes forKey:@"allTimes"];  
  48. }  
  49.   
  50. @end  

[objc] view plaincopy在CODE上查看代码片派生到我的代码片
  1. //  
  2. //  Athlete.h  
  3. //  ArchiverDemo  
  4. //  
  5. //  Created by swplzj on 13-11-19.  
  6. //  Copyright (c) 2013年 swplzj. All rights reserved.  
  7. //  
  8.   
  9. #import <Foundation/Foundation.h>  
  10.   
  11. @class ScoreCard;  
  12.   
  13. //遵守NSCoding 协议  
  14. @interface Athlete : NSObject<NSCoding>  
  15. {  
  16.     NSString *_name;  
  17.     NSString *_bio;  
  18.     NSString *_phoneNumber;  
  19.     ScoreCard *_scoreCard;  
  20.     BOOL _eligible;  
  21. }  
  22.   
  23. @property (copyNSString *name, *bio, *phoneNumber;  
  24. @property (retainScoreCard *scoreCard;  
  25. @property (getter = isEligible) BOOL eligible;  
  26.   
  27. - (void)print;  
  28.   
  29. @end  

[objc] view plaincopy在CODE上查看代码片派生到我的代码片
  1. //  
  2. //  Athlete.m  
  3. //  ArchiverDemo  
  4. //  
  5. //  Created by swplzj on 13-11-19.  
  6. //  Copyright (c) 2013年 swplzj. All rights reserved.  
  7. //  
  8.   
  9. #import "Athlete.h"  
  10. #import "ScoreCard.h"  
  11.   
  12. @implementation Athlete  
  13.   
  14. @synthesize name = _name, bio = _bio, phoneNumber = _phoneNumber, scoreCard = _scoreCard, eligible = _eligible;  
  15.   
  16. - (void)dealloc  
  17. {  
  18.     [_name release];  
  19.     [_bio release];  
  20.     [_scoreCard release];  
  21.   
  22.     [super dealloc];  
  23. }  
  24.   
  25. - (id)init  
  26. {  
  27.     if (self = [super init]) {  
  28.         _name = [[NSString alloc] init];  
  29.         _bio = [[NSString alloc] init];  
  30.         _phoneNumber = [[NSString alloc] init];  
  31.         _scoreCard = [[ScoreCard alloc] init];  
  32.         _eligible = YES;  
  33.     }  
  34.     return self;  
  35. }  
  36.   
  37. //解码方法  
  38. - (id)initWithCoder:(NSCoder *)aDecoder  
  39. {  
  40.     if (self = [super init]) {  
  41.         _name = [[aDecoder decodeObjectForKey:@"name"] retain];  
  42.         _bio = [[aDecoder decodeObjectForKey:@"bio"] retain];  
  43.         _scoreCard = [[aDecoder decodeObjectForKey:@"scoreCard"] retain];  
  44.         //BOOL类型变量解码  
  45.         _eligible = [aDecoder decodeBoolForKey:@"eligible"];  
  46.     }  
  47.       
  48.     return self;  
  49. }  
  50.   
  51. //编码方法  
  52. - (void)encodeWithCoder:(NSCoder *)aCoder  
  53. {  
  54.     [aCoder encodeObject:_name forKey:@"name"];  
  55.     [aCoder encodeObject:_bio forKey:@"bio"];  
  56.     [aCoder encodeObject:_scoreCard forKey:@"scoreCard"];  
  57.     //BOOL类型变量归档  
  58.     [aCoder encodeBool:_eligible forKey:@"eligible"];  
  59. }  
  60.   
  61. - (void)print  
  62. {  
  63.     NSLog(@"Name: %@\nBio: %@\nTel: %@\n\nBest Time: %@\n\nAll Times:", _name, _bio, _phoneNumber, [_scoreCard bestTime]);  
  64.     for (NSString *time in [_scoreCard allTimes]) {  
  65.         NSLog(@"%@", time);  
  66.     }  
  67. }  
  68.   
  69. @end  

[objc] view plaincopy在CODE上查看代码片派生到我的代码片
  1. //  
  2. //  Roster.h  
  3. //  ArchiverDemo  
  4. //  
  5. //  Created by swplzj on 13-11-19.  
  6. //  Copyright (c) 2013年 swplzj. All rights reserved.  
  7. //  
  8.   
  9. #import <Foundation/Foundation.h>  
  10.   
  11. @class Athlete;  
  12.   
  13. //遵循归档NSCoding协议  
  14. @interface Roster : NSObject<NSCoding>  
  15. {  
  16.     NSMutableArray *_athletes;  
  17.     int _rank;  
  18. }  
  19.   
  20. @property (retainNSMutableArray *athletes;  
  21. @property int rank;  
  22.   
  23. - (void)create;  
  24. - (void)print;  
  25. - (void)addAthlete:(Athlete *)athlete;  
  26.   
  27. @end  

[objc] view plaincopy在CODE上查看代码片派生到我的代码片
  1. //  
  2. //  Roster.m  
  3. //  ArchiverDemo  
  4. //  
  5. //  Created by swplzj on 13-11-19.  
  6. //  Copyright (c) 2013年 swplzj. All rights reserved.  
  7. //  
  8.   
  9. #import "Roster.h"  
  10. #import "ScoreCard.h"  
  11. #import "Athlete.h"  
  12.   
  13. static NSString *names [] = { @"John Doe",  
  14.     @"Jane Doe"@"Shaun White"@"Jeff Beck",  
  15.     @"Eric Clapton"@"Angus Young"@"Flavius Josephus" };  
  16.   
  17. @implementation Roster  
  18.   
  19. @synthesize athletes = _athletes, rank = _rank;  
  20.   
  21. - (void)dealloc  
  22. {  
  23.     [_athletes release];  
  24.       
  25.     [super dealloc];  
  26. }  
  27.   
  28. - (void)create  
  29. {  
  30.     NSMutableArray *scoreArray = [NSMutableArray arrayWithObjects:@"21:32:21"@"12:48:11"@"16:11:32", nil nil];  
  31.     for(int i = 0; i < 7; ++i){  
  32.         Athlete *athlete = [[Athlete alloc] init];  
  33.         athlete.name = names[i];  
  34.         athlete.bio = @"I'm a boss";  
  35.         [athlete setPhoneNumber:@"321-3241"];  
  36.         athlete.scoreCard.bestTime = @"12:30:22";  
  37.         athlete.scoreCard.allTimes = scoreArray;  
  38.         [self addAthlete:athlete];  
  39.         [athlete release];  
  40.     }  
  41. }  
  42.   
  43. - (id)init  
  44. {  
  45.     if (self = [super init]) {  
  46.         _rank = 0;  
  47.         _athletes = [[NSMutableArray alloc] init];  
  48.     }  
  49.     return self;  
  50. }  
  51.   
  52. //解码方法  
  53. - (id)initWithCoder:(NSCoder *)aDecoder  
  54. {  
  55.     if (self = [super init]) {  
  56.         _athletes = [[aDecoder decodeObjectForKey:@"athletes"] retain];  
  57.         //解码int类型变量  
  58.         _rank = [aDecoder decodeIntForKey:@"rank"];  
  59.     }  
  60.     return self;  
  61. }  
  62.   
  63. - (void)encodeWithCoder:(NSCoder *)aCoder  
  64. {  
  65.     [aCoder encodeObject:_athletes forKey:@"athletes"];  
  66.     [aCoder encodeInt:_rank forKey:@"rank"];  
  67. }  
  68.   
  69. - (void)addAthlete:(Athlete *)athlete  
  70. {  
  71.     [_athletes addObject:athlete];  
  72. }  
  73.   
  74. - (void)print  
  75. {  
  76.     NSLog(@"Roster info:\nRank: %d", _rank);  
  77.     for (Athlete *athlete in _athletes) {  
  78.         NSLog(@"%@", [athlete name]);  
  79.     }  
  80. }  
  81.   
  82. @end  

在main函数里面进行归档

[objc] view plaincopy在CODE上查看代码片派生到我的代码片
  1. //  
  2. //  main.m  
  3. //  ArchiverDemo  
  4. //  
  5. //  Created by swplzj on 13-11-19.  
  6. //  Copyright (c) 2013年 swplzj. All rights reserved.  
  7. //  
  8.   
  9. #import <UIKit/UIKit.h>  
  10. #import "Roster.h"  
  11.   
  12. #define ARCHIVE 0  
  13. #define UNARCHIVE 1  
  14.   
  15. int main(int argc, charchar *argv[])  
  16. {  
  17.     NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];  
  18.     //获得根路径  
  19.     NSString *homePath = [[NSBundle mainBundle] executablePath];  
  20.     //按照“/”分解字符串到数组  
  21.     NSArray *strings = [homePath componentsSeparatedByString:@"/"];  
  22.     //  
  23.     NSString *executbleName = [strings objectAtIndex:[strings count] - 1];  
  24.     NSString *baseDirectory = [homePath substringToIndex:[homePath length] - [executbleName length] - 1];  
  25.     //文件名字  
  26.     NSString *fileName = [NSString stringWithFormat:@"%@/roster.archive", baseDirectory];  
  27.     NSLog(@"filePath: %@", fileName);  
  28.   
  29. #if ARCHIVE  
  30.     //创建并归档一个roster  
  31.     Roster *roster = [[Roster alloc] init];  
  32.     [roster create];  
  33.     //把对象写到二进制流中去  
  34.     [NSKeyedArchiver archiveRootObject:roster toFile:fileName];  
  35.     [roster release];  
  36. #endif  
  37.       
  38. #if UNARCHIVE  
  39.     //已经写入到磁盘,直接从二进制流读取对象  
  40.     Roster *unarchive = [NSKeyedUnarchiver unarchiveObjectWithFile:fileName];  
  41.     [unarchive print];  
  42.     for (Athlete *athlete in [unarchive athletes]) {  
  43.         [athlete print];  
  44.     }  
  45.     [unarchive release];  
  46. #endif  
  47.       
  48.     [pool release];  
  49.       
  50.     return 0;  
  51. }  
运行程序,前往文件夹:

/Users/issuser/Library/Application Support/iPhone Simulator/6.1/Applications/74C8943C-BE5F-4BB7-8385-8E922AF29589/ArchiverDemo.app/roster.archive


归档成功。点击这里下载ArchiverDemo

这就是使用归档来达到数据的持久化。你也来试试吧。

0 0