简体   繁体   English

在Objective-C中归档对象中的对象

[英]Archiving objects within objects in objective-c

Thankyou for reading, 谢谢您的阅读,

PS: I am a beginner so I am not too good at this unfortunetaly, but any help would be very appreciated PS:我是一个初学者,所以我对此不太幸运,但是任何帮助将不胜感激。

So basically I want to archive a big array which contains Account objects, which they themselves contain: 所以基本上我想存档一个包含Account对象的大数组,它们本身包含:

  • 1.a username in form of a NSString, 1.以NSString形式的用户名,

  • 2.an encrypted password array filled with NSNumbers, and 2.一个加密的密码数组,其中填充了NSNumbers,以及

  • 3. a data array filled with service data objects. 3. 填充有服务数据对象的数据数组。

The service data objects have the following: 服务数据对象具有以下内容:

    1. encrypted serviceType (NSArray filled with NSNumbers) (whatever service the username and password is for) 加密的serviceType(用NSNumbers填充的NSArray)(无论用户名和密码用于什么服务)
    1. encrypted username (NSArray filled with NSNumbers) 加密的用户名(用NSNumbers填充的NSArray)
    1. encrypted password (NSArray filled with NSNumbers) 加密密码(用NSNumbers填充的NSArray)

Now weirdly when trying to archive and save this, I get two errors. 现在奇怪的是,当尝试存档和保存它时,出现两个错误。 One time it won't let me add service data objects to the data array in the Account class anymore, with the following error message (or at least they dont show up in the NSTableView I have, however it does say they exsist): 一次它不会让我再将服务数据对象添加到Account类的数据数组中,并显示以下错误消息(或者至少它们不会显示在我拥有的NSTableView中,但是它确实存在):

[<ServiceData 0x60000023bfa0> valueForUndefinedKey:]: this class is not key value
coding-compliant for the key service.

and two, when I try to login in the the username and password from the Account class, it retrieves the username and the first couple and last couple NSNumbers of my password correctly, but the rest of the NSNumbers for the password are in the trillions or something, so I'm wondering what is going wrong, any help would be greatly appreciated. 第二,当我尝试从Account类中登录用户名和密码时,它会正确检索用户名以及我的密码的前两个NSNumber和最后两个NSNumber,但其余的NSNumber则以万亿或的东西,所以我想知道出了什么问题,任何帮助将不胜感激。

Here is the code for my instance variables, how I used the NSKeyedArchiver and unarchiver, and how I went about saving and loading the files. 这是我的实例变量的代码,如何使用NSKeyedArchiver和unarchiver,以及如何保存和加载文件。 Again, please help me, I have been stuck on this for a while and this is kind-of my last resort. 再次,请帮助我,我已经坚持了一段时间,这是我的最后选择。 I have no idea what is happening! 我不知道发生了什么!


ACCOUNT CLASS: 帐户类别:

H file: H档:

@interface Account : NSObject <NSCoding>
{
@private
    NSString *username;
    NSMutableArray *password;
    NSMutableArray *accData;
}

@property NSString *username;
@property NSArray *password;

FULL M file: 完整的M文件:

-(id)initWithCoder:(NSCoder *)aDecoder
{
    self = [super init];
    if(self)
    {
        username = [aDecoder decodeObjectForKey:@"username"];
        password = [aDecoder decodeObjectForKey:@"password"];
        accData = [aDecoder decodeObjectForKey:@"data"];
    }
    return self;
}

-(void)encodeWithCoder:(NSCoder *)aCoder
{
    [aCoder encodeObject:username forKey:@"username"];
    [aCoder encodeObject:password forKey:@"password"];
    [aCoder encodeObject:accData forKey:@"data"];
}

SERVICEDATA CLASS: SERVICEDATA类别:

H file: H档:

@interface ServiceData : NSObject <NSCoding>
{
@private
    NSArray* serviceData;
    NSArray* usernameData;
    NSArray* passwordData;
}

@property NSArray* serviceData; 
@property NSArray* usernameData;
@property NSArray* passwordData;

M file: M档:

#import "Account.h"
#import "Crypt.h"

NSMutableArray *accounts;
NSInteger accountNumber = -1;


@implementation Account

@synthesize username;
@synthesize password;

- (id)initWithUsername:(NSString *)name withPassword:(NSMutableArray *)key
{
    self = [super init];
    if (self)
    {
        username = name;
        password = key;
        accData = [[NSMutableArray alloc]init];
    }
    return self;
}


/*
setters and getters
*/

-(NSString*)getUsername;
{
    return username;
}
-(NSArray*)getPassword;
{
    return password;
}
-(void)changePassword:(NSMutableArray*)newPassword;
{
    NSInteger sizeOldPass = [password count];
    NSInteger sizeNewPass = [newPassword count];
    int changeXObjects = (int)(sizeNewPass - sizeOldPass);
    int changeSize = abs(changeXObjects);
    //adjusts size differences
    if (changeXObjects < 0)
    {
        for(int i = 0; i < changeSize; i++)
        {
            [password removeLastObject];
        }
    }
    else if (changeXObjects > 0)
    {
        for(int i = 0; i < changeSize; i++)
        {
            NSNumber *value = [NSNumber numberWithInt:0];
            [password addObject:value];
        }
    }

    //change password
    NSInteger sizePass = [password count];
    for (int k = 0; k < sizePass; k++)
    {
        [password replaceObjectAtIndex:k withObject:newPassword[k]];
    }
}

-(NSMutableArray*)getAccData;
{
    return accData;
}
-(void)setAccData:(NSMutableArray*)input
{
    [input setArray: accData];
}

+(NSMutableArray*)getAccounts
{
    return accounts;
}

+(NSInteger)getAccountNumber
{
    return accountNumber;
}

+(void)setAccounts:(id)accs
{
    accounts = accs;
}

+(void)setAccountNumber:(NSInteger)number
{
    accountNumber = number;
}


/*
other methods
*/

+(void)addAccount:(id)acc
{
    [accounts addObject:acc];
}
+(void)deleteAccount:(NSInteger)index
{
    [accounts removeObjectAtIndex:index];
}


-(void)addAccData:(id)input
{
    [accData addObject:input];
}

-(void)deleteAccDataAt:(NSInteger)index
{
    [accData removeObjectAtIndex:index];
}

+(bool)checkPassword:(NSString*)passwordIn accountNumber:(NSInteger)index
{
    NSMutableArray *passwordInputCrypt = [Crypt encrypt:passwordIn];
    NSMutableArray *passwordCrypt = [accounts[index] getPassword];

    NSInteger lengthPassword = [passwordInputCrypt count];

    bool correctPassword = true;
    if([passwordCrypt count] == [passwordInputCrypt count])
    {
        for(int i = 0; i < lengthPassword; i++)
        {
            if(passwordCrypt[i]!=passwordInputCrypt[i])
                correctPassword = false;
        }
    }
    else
    {
        correctPassword = false;
    }

    if(correctPassword == true)
    {
        return true;
    }
    return false;
}


-(id)initWithCoder:(NSCoder *)aDecoder
{
    self = [super init];
    if(self)
    {
        username = [aDecoder decodeObjectForKey:@"username"];
        password = [aDecoder decodeObjectForKey:@"password"];
        accData = [aDecoder decodeObjectForKey:@"data"];
    }
    return self;
}

-(void)encodeWithCoder:(NSCoder *)aCoder
{
    [aCoder encodeObject:username forKey:@"username"];
    [aCoder encodeObject:password forKey:@"password"];
    [aCoder encodeObject:accData forKey:@"data"];
}
@end

LOADING FILE(filePath is given): 加载文件(给定filePath):

NSData *data = [[NSFileManager defaultManager] contentsAtPath:filePath];

if(data != nil)
{
    NSArray *arrayFromData = [NSKeyedUnarchiver unarchiveObjectWithData:data];
    NSMutableArray *initArray = [NSMutableArray arrayWithArray:arrayFromData];
    [Account setAccounts:initArray];
}
else
{
    NSMutableArray *accountsInit = [[NSMutableArray alloc] init];
    [Account setAccounts:accountsInit];
}

SAVING FILE: 保存文件:

NSArray *accounts = [Account getAccounts];
NSString *filePath = [AppController getFilePath];
NSData *data = [NSKeyedArchiver archivedDataWithRootObject:accounts];

[data writeToFile:filePath atomically:YES];

A few things: 一些东西:

  1. You should not be archiving password data to disk (even if you are encrypting it). 您不应该将密码数据归档到磁盘上(即使您正在对其进行加密)。 That's what the keychain is for. 这就是钥匙串的用途。 Have a look at SSKeychain for a good wrapper class. 看看SSKeychain是一个好的包装类。
  2. The Key-value coding error you are getting suggests you are trying to reference your serviceData array as just "service" somewhere. 您收到的键值编码错误表明您正在尝试将serviceData数组引用为某处的“服务”。 Check your valueForKey and setValueForKey statements. 检查您的valueForKey和setValueForKey语句。

Can you post the rest of the Account class? 您可以发布其余的Account类吗? That method setAccounts looks like it might be relevant. 该方法setAccounts看起来可能是相关的。

Also is there a reason you are using Keyed Archiving instead of Core Data? 另外,您是否有理由使用键控归档而不是核心数据?

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM