Objective c NSKeyedUnachiver发现损坏的数据

Objective c NSKeyedUnachiver发现损坏的数据,objective-c,cocoa,nskeyedarchiver,nskeyedunarchiver,Objective C,Cocoa,Nskeyedarchiver,Nskeyedunarchiver,我有一个归档程序和一个非归档程序,它们一起工作 第二个程序的运行结果表明,尽管两个对象(myFoo1)中的一个已很好地存档、存储并在以后未存档,但另一个(myBook)似乎无法正确地未存档。我只是不知道归档和/或未归档过程中发生了什么,这些过程似乎破坏了部分原始数据。我已仔细确保编码键与解码键相同,但程序仍然存在 归档程序的代码: #import <Foundation/Foundation.h> @interface Foo : NSObject <NSCoding>

我有一个归档程序和一个非归档程序,它们一起工作

第二个程序的运行结果表明,尽管两个对象(myFoo1)中的一个已很好地存档、存储并在以后未存档,但另一个(myBook)似乎无法正确地未存档。我只是不知道归档和/或未归档过程中发生了什么,这些过程似乎破坏了部分原始数据。我已仔细确保编码键与解码键相同,但程序仍然存在

归档程序的代码:

#import <Foundation/Foundation.h>

@interface Foo : NSObject <NSCoding>

@property (copy, nonatomic) NSString * strVal;
@property int intVal;
@property float floatVal;

-(void) display;

@end

#import "Foo.h"

@implementation Foo

@synthesize  strVal, intVal, floatVal;

-(void) encodeWithCoder:(NSCoder *)aCoder
{
    [aCoder encodeObject: strVal forKey: @"FoostrVal"];
    [aCoder encodeInt: intVal forKey: @"FoointVal"];
    [aCoder encodeFloat: floatVal forKey: @"FoofloatVal"];
    // NSLog (@"Foo encodeWithCoder called"); called
}

-(id) initWithCoder:(NSCoder *)aDecoder
{
    strVal = [aDecoder decodeObjectForKey: @"FoostrVal"];
    intVal = [aDecoder decodeIntForKey: @"FoointVal"];
    floatVal = [aDecoder decodeFloatForKey: @"FoofloatVal"];
    // NSLog (@"Foo initWithCoder called"); not called
    return self;
}

-(void) display
{
    NSLog (@"%@ %i %g", strVal, intVal, floatVal);
}

@end

#import <Foundation/Foundation.h>

@interface AddressCard : NSObject <NSCoding>

@property (nonatomic, copy) NSString * name, * email;

-(instancetype) initWithName: (NSString *) theName andEmail: (NSString *) theEmail;
-(void) showCard;

@end

#import "AddressCard.h"

@implementation AddressCard

@synthesize name, email;

-(instancetype) initWithName: (NSString *) theName andEmail: (NSString *) theEmail
{
    self = [super init];
    if (self) {
        self.name = [NSString stringWithString: theName];
        self.email = [NSString stringWithString: theEmail];
    }
    return self;
}

-(instancetype) init
{
    return [self initWithName: @"NoName" andEmail: @"NoEmail"];
}

-(void) encodeWithCoder:(NSCoder *)aCoder
{
    [aCoder encodeObject: name forKey: @"AddrCardName"];
    [aCoder encodeObject: email forKey: @"AddrCardEmail"];
    // NSLog (@"AddressCard encodeWithCoder called"); called
}

-(id) initWithCoder:(NSCoder *)aDecoder
{
    [aDecoder decodeObjectForKey: @"AddrCardName"];
    [aDecoder decodeObjectForKey: @"AddrCardEmail"];
    // NSLog (@"AddressCard initWithCoder called"); not called

    return self;
}

-(void) showCard
{
    NSLog (@"%-20s%-40s", [name UTF8String], [email UTF8String]);
}

@end

#import "AddressCard.h"

@interface AddressBook : NSObject <NSCoding>

@property (nonatomic, copy) NSString * title;
@property (nonatomic, strong) NSMutableArray * book;

-(instancetype) initWithTitle: (NSString *) title;
-(void) addCard: (AddressCard *) card;
-(void) list;

@end

#import "AddressBook.h"

@implementation AddressBook

@synthesize title, book;

-(instancetype) initWithTitle: (NSString *) theTitle
{
    self = [super init];
    if (self) {
        title = [NSString stringWithString: theTitle];
        book = [NSMutableArray array];
    }
    return self;
}

-(instancetype) init
{
    return [self initWithTitle: @"NoTitle"];
}

-(void) encodeWithCoder:(NSCoder *)aCoder
{
    [aCoder encodeObject: title forKey: @"AddrBookTitle"];
    [aCoder encodeObject: book forKey: @"AddrBookBook"];
    // NSLog (@"AddressBook encodeWithCoder called"); called
}

-(id) initWithCoder:(NSCoder *)aDecoder
{
    [aDecoder decodeObjectForKey: @"AddrBookTitle"];
    [aDecoder decodeObjectForKey: @"AddrBookBook"];
    // NSLog (@"AddressBook initWithCoder called"); not called

    return self;
}

-(void) addCard: (AddressCard *) card
{
    if ([book containsObject: card] == YES)
        NSLog (@"The card already exists in %@", title);
    else
        [book addObject: card];
}

-(void) list
{
    for (AddressCard * card in book)
        [card showCard];
}

@end

#import "AddressBook.h"
#import "Foo.h"

int main(int argc, const char * argv[]) {
    @autoreleasepool {
        Foo * myFoo1 = [[Foo alloc] init];
        NSMutableData * dataArea;
        NSKeyedArchiver * archiver;
        AddressBook * myBook = [[AddressBook alloc] initWithTitle: @"Steve's Address Book"];

        NSString * aName = @"Julia Kochan";
        NSString * aEmail = @"jewls337@axlc.com";
        NSString * bName = @"Tony Iannino";
        NSString * bEmail = @"tony.iannino@tecfitness.com";
        NSString * cName = @"Stephen Kochan";
        NSString * cEmail = @"steve@steve_kochan.com";
        NSString * dName = @"Jamie Baker";
        NSString * dEmail = @"jbaker@hitmail.com";
        NSString * filePath = @"addrbook.arch";

        AddressCard * card1 = [[AddressCard alloc] initWithName: aName andEmail: aEmail];
        AddressCard * card2 = [[AddressCard alloc] initWithName: bName andEmail: bEmail];
        AddressCard * card3 = [[AddressCard alloc] initWithName: cName andEmail: cEmail];
        AddressCard * card4 = [[AddressCard alloc] initWithName: dName andEmail: dEmail];

        // Add some cards to the address book
        [myBook addCard: card1];
        [myBook addCard: card2];
        [myBook addCard: card3];
        [myBook addCard: card4];

        myFoo1.strVal = @"This is the string";
        myFoo1.intVal = 12345;
        myFoo1.floatVal = 99.8;

        // Set up a data area and connect it to an NSKeyedArchiver object
        dataArea = [NSMutableData data];
        archiver = [[NSKeyedArchiver alloc] initForWritingWithMutableData: dataArea];

        // Now we can begin to archive objects
        [archiver encodeObject: myBook forKey: @"myaddrbook"];
        [archiver encodeObject: myFoo1 forKey: @"myfoo1"];
        [archiver finishEncoding];

        // Write the archived data area to a file
        if ([dataArea writeToFile: filePath atomically: YES] == NO)
            NSLog (@"Archiving failed!");
        NSLog (@"All operations successful!");

    }
    return 0;
}
#import <Foundation/Foundation.h>

@interface Foo : NSObject <NSCoding>

@property (copy, nonatomic) NSString * strVal;
@property int intVal;
@property float floatVal;

-(void) display;

@end

#import "Foo.h"

@implementation Foo

@synthesize  strVal, intVal, floatVal;

-(void) encodeWithCoder:(NSCoder *)aCoder
{
    [aCoder encodeObject: strVal forKey: @"FoostrVal"];
    [aCoder encodeInt: intVal forKey: @"FoointVal"];
    [aCoder encodeFloat: floatVal forKey: @"FoofloatVal"];
    // NSLog (@"Foo encodeWithCoder called"); not called
}

-(id) initWithCoder:(NSCoder *)aDecoder
{
    strVal = [aDecoder decodeObjectForKey: @"FoostrVal"];
    intVal = [aDecoder decodeIntForKey: @"FoointVal"];
    floatVal = [aDecoder decodeFloatForKey: @"FoofloatVal"];
    // NSLog (@"Foo initWithCoder called"); called

    return self;
}

-(void) display
{
    NSLog (@"%@\n%i\n%g", strVal, intVal, floatVal);
}

@end

#import <Foundation/Foundation.h>

@interface AddressCard : NSObject <NSCoding>

@property (nonatomic, copy) NSString * name, * email;

-(instancetype) initWithName: (NSString *) theName andEmail: (NSString *) theEmail;
-(void) showCard;

@end

#import "AddressCard.h"

@implementation AddressCard

@synthesize name, email;

-(instancetype) initWithName: (NSString *) theName andEmail: (NSString *) theEmail
{
    self = [super init];
    if (self) {
        self.name = [NSString stringWithString: theName];
        self.email = [NSString stringWithString: theEmail];
    }
    return self;
}

-(instancetype) init
{
    return [self initWithName: @"NoName" andEmail: @"NoEmail"];
}

-(void) encodeWithCoder:(NSCoder *)aCoder
{
    [aCoder encodeObject: name forKey: @"AddrCardName"];
    [aCoder encodeObject: email forKey: @"AddrCardEmail"];
    // NSLog (@"AddressCard encodeWithCoder called"); not called
}

-(id) initWithCoder:(NSCoder *)aDecoder
{
    [aDecoder decodeObjectForKey: @"AddrCardName"];
    [aDecoder decodeObjectForKey: @"AddrCardEmail"];
    // NSLog (@"AddressCard initWithCoder called"); called

    return self;
}

-(void) showCard
{
    NSLog (@"%-20s%-40s", [name UTF8String], [email UTF8String]);
}

@end

#import "AddressCard.h"

@interface AddressBook : NSObject <NSCoding>

@property (nonatomic, copy) NSString * title;
@property (nonatomic, strong) NSMutableArray * book;

-(instancetype) initWithTitle: (NSString *) title;
-(void) addCard: (AddressCard *) card;
-(void) list;

@end

#import "AddressBook.h"

@implementation AddressBook

@synthesize title, book;

-(instancetype) initWithTitle: (NSString *) theTitle
{
    self = [super init];
    if (self) {
        title = [NSString stringWithString: theTitle];
        book = [NSMutableArray array];
    }
    return self;
}

-(void) encodeWithCoder:(NSCoder *)aCoder
{
    [aCoder encodeObject: title forKey: @"AddrBookTitle"];
    [aCoder encodeObject: book forKey: @"AddrBookBook"];
    // NSLog (@"AddressBook encodeWithCoder called"); not called

}

-(id) initWithCoder:(NSCoder *)aDecoder
{
    [aDecoder decodeObjectForKey: @"AddrBookTitle"];
    [aDecoder decodeObjectForKey: @"AddrBookBook"];
    // NSLog (@"AddressBook initWithCoder called"); called

    return self;
}

-(void) addCard: (AddressCard *) card
{
    if ([book containsObject: card] == YES)
        NSLog (@"The card already exists in %@", title);
    else
        [book addObject: card];
}

-(void) list
{
    for (AddressCard * card in book)
        [card showCard];
}

@end

#import "AddressBook.h"
#import "Foo.h"

int main(int argc, const char * argv[]) {
    @autoreleasepool {
        NSData * dataArea;
        NSKeyedUnarchiver * unarchiver;
        Foo * myFoo1;
        AddressBook * myBook;
        NSString * filePath = @"addrbook.arch";

        // Read in the archive and connect an
        // NSkeyedUnarchiver object to it

        dataArea = [NSData dataWithContentsOfFile: filePath];
        if (!dataArea) {
            NSLog (@"Can't read back archive file!");
            return 1;
        }
        unarchiver = [[NSKeyedUnarchiver alloc] initForReadingWithData: dataArea];
        // Decode the objects we previously stored in the archive
        myBook = [unarchiver decodeObjectForKey: @"myaddrbook"];
        myFoo1 = [unarchiver decodeObjectForKey: @"myfoo1"];
        [unarchiver finishDecoding];

        // Verify that the resote was successful
        if (myBook != nil) {
            if ([myBook.book count] == 0)
                NSLog (@"Data corrupted in myBook!");
            else
                [myBook list];
        }
        else
            NSLog (@"Load myBook failed!");

        if (myFoo1 != nil)
            [myFoo1 display];
        else
            NSLog (@"Load myFoo1 failed!");
    }
    return 0;
}
#导入
@接口Foo:NSObject
@属性(复制,非原子)NSString*strVal;
@属性int intVal;
@财产浮动;
-(d)显示;
@结束
#导入“Foo.h”
@执行Foo
@合成strVal、intVal、floatVal;
-(void)编码器与编码器:(NSCoder*)一个编码器
{
[A编码对象:strVal forKey:@“FoostrVal”];
[aCoder encodeInt:intVal forKey:@“FoointVal”];
[aCoder encodeFloat:floatVal-forKey:@“foodfloatval”];
//NSLog(@“Foo encoder with coder called”);已调用
}
-(id)initWithCoder:(NSCoder*)aDecoder
{
strVal=[aDecoder-decodeObjectForKey:@“FoostrVal”];
intVal=[aDecoder decodeIntForKey:@“FoointVal”];
floatVal=[aDecoder-decodeFloatForKey:@“FoodFloatVal”];
//NSLog(@“Foo initWithCoder已调用”);未调用
回归自我;
}
-(无效)显示
{
NSLog(@“%@%i%g”、strVal、intVal、floatVal);
}
@结束
#进口
@接口地址卡:NSObject
@属性(非原子,副本)NSString*名称,*电子邮件;
-(instancetype)initWithName:(NSString*)名称和邮件:(NSString*)邮件;
-(作废)展示卡;
@结束
#导入“AddressCard.h”
@实现地址卡
@综合姓名、电子邮件;
-(instancetype)initWithName:(NSString*)名称和邮件:(NSString*)邮件
{
self=[super init];
如果(自我){
self.name=[nsstringwithstring:theName];
self.email=[nsstringwithstring:theEmail];
}
回归自我;
}
-(instancetype)初始化
{
return[self initWithName:@“NoName”and mail:@“NoEmail”];
}
-(void)编码器与编码器:(NSCoder*)一个编码器
{
[aCoder encodeObject:name forKey:@“AddrCardName”];
[aCoder encodeObject:email forKey:@“AddrCardEmail”];
//NSLog(@“AddressCard Encoder With Coder called”);已调用
}
-(id)initWithCoder:(NSCoder*)aDecoder
{
[aDecoder decodeObjectForKey:@“AddrCardName”];
[aDecoder decodeObjectForKey:@“AddrCardEmail”];
//NSLog(@“已调用AddressCard initWithCoder”);未调用
回归自我;
}
-(作废)展示卡
{
NSLog(@“%-20s%-40s”,[name UTF8String],[email UTF8String]);
}
@结束
#导入“AddressCard.h”
@接口地址簿:NSObject
@属性(非原子,副本)NSString*标题;
@属性(非原子,强)NSMutableArray*book;
-(instancetype)initWithTitle:(NSString*)标题;
-(作废)添加卡:(地址卡*)卡;
-(作废)名单;
@结束
#导入“AddressBook.h”
@实施通讯录
@综合书名、书籍;
-(instancetype)initWithTitle:(NSString*)标题
{
self=[super init];
如果(自我){
title=[nsstringwithstring:theTitle];
book=[NSMutableArray];
}
回归自我;
}
-(instancetype)初始化
{
return[self initWithTitle:@“NoTitle”];
}
-(void)编码器与编码器:(NSCoder*)一个编码器
{
[aCoder encodeObject:title forKey:@“AddrBookTitle”];
[aCoder encodeObject:book forKey:@“AddrBookBook”];
//NSLog(@“AddressBook Encoder WithCoder called”);已调用
}
-(id)initWithCoder:(NSCoder*)aDecoder
{
[aDecoder decodeObjectForKey:@“AddrBookTitle”];
[aDecoder decodeObjectForKey:@“AddrBook”];
//NSLog(@“AddressBook initWithCoder已调用”);未调用
回归自我;
}
-(无效)添加卡:(地址卡*)卡
{
如果([book containsObject:card]==是)
NSLog(@“卡已存在于%@”,标题);
其他的
[图书添加对象:卡片];
}
-(作废)名单
{
用于(地址卡*书本中的卡)
[卡片展示卡];
}
@结束
#导入“AddressBook.h”
#导入“Foo.h”
int main(int argc,const char*argv[]{
@自动释放池{
Foo*myFoo1=[[Foo alloc]init];
NSMutableData*数据区;
NSKeyedArchiver*archiver;
AddressBook*myBook=[[AddressBook alloc]initWithTitle:@“史蒂夫的通讯录”];
NSString*aName=@“Julia Kochan”;
NSString*aEmail=@”jewls337@axlc.com";
NSString*bName=@“Tony Iannino”;
NSString*bEmail=@“tony。iannino@tecfitness.com";
NSString*cName=@“Stephen Kochan”;
NSString*cEmail=@”steve@steve_kochan.com";
NSString*dName=@“杰米·贝克”;
NSString*dEmail=@”jbaker@hitmail.com";
NSString*filePath=@“addrbook.arch”;
AddressCard*card1=[[AddressCard alloc]initWithName:aName and mail:aEmail];
AddressCard*card2=[[AddressCard alloc]initWithName:bName和Mail:bEmail];
AddressCard*card3=[[AddressCard alloc]initWithName:cName and Mail:cEmail];
AddressCard*card4=[[AddressCard alloc]initWithName:dName和Mail:dEmail];
//在通讯簿中添加一些卡片
[myBook addCard:card1];
[myBook addCard:card2];
[myBook addCard:card3];
[myBook addCard:card4];
myFoo1.strVal=@“这是字符串”;
myFoo1.intVal=12345;
myFoo1.floatVal=99.8;
//设置数据区域并将其连接到NSKeyedArchiver对象
dataArea=[NSMutableData];
archiver=[[NSKeyedArchiver alloc]initForWritingWithMutableData:dataArea];
//现在我们可以开始归档对象了
[archiver encodeObject:myBook forKey:@“myaddrbook”];
[archiver encodeObject:myFoo1-forKey:@“myFoo1”];
[archiver finishEncoding];
//将存档数据区域写入文件
if([dataArea writeToFile:filePath原子性:是]==否)
NSLog(@“存档失败!”);
NSLog(@“所有操作