我有一个非常奇怪的错误,我试图追踪几天。我将游戏的状态数据保存在应用程序的Documents目录中的文件中。
在最近的iOS更新之前,一切都运行良好(不确定何时,大约在9.0左右)。突然之间,数据没有正确归档/取消归档。
奇怪的部分是当我从Xcode运行它时,代码工作正常,iPad连接到我的MAC或在模拟器中。当我使用TestFlight从iTunes下载应用程序时,它不再有效。这使得调试非常困难。
我已经检查并仔细检查了所有内容,我正在使用URL路径,添加了错误捕获代码等,但是当通过TestFlight从iTunes安装应用程序时,归档无法正常工作。
作为最后的手段,我添加了新的代码来存档我的对象,立即将其解压缩到另一个变量中,然后在标签中显示一些数据。生成的对象包含空数据。
不会抛出异常。
重申一下,当从iTunes安装应用程序时,代码不起作用。
以下是代码段;
NSString *documentDirectory = [[[[NSFileManager defaultManager] URLsForDirectory:NSDocumentDirectory inDomains:NSUserDomainMask] lastObject] path];
NSString* filePath = [documentDirectory stringByAppendingPathComponent:@"playerTest.data"];
LBYPlayerData* pd1 = [[LBYPlayerData alloc ]init];
pd1.currentCountryID = 1;
pd1.lsn = @"123.456";
BOOL success = [NSKeyedArchiver archiveRootObject:pd1 toFile:filePath];
NSAssert(success, @"archiveRootObject failed");
LBYPlayerData* pd2 = nil;
@try {
pd2 = [NSKeyedUnarchiver unarchiveObjectWithFile:filePath];
} @catch (NSException *exception) {
playerDataLabel.text = [NSString stringWithFormat:@"%@",exception.name];
playerUndoDataLabel.text = [NSString stringWithFormat:@"%@",exception.description];
} @finally {
NSAssert((pd2 != nil), @"archivePlayerDataUndo failed to unarchive");
playerDataLabel.text = [NSString stringWithFormat:@"path: %@",filePath];
playerUndoDataLabel.text = [NSString stringWithFormat:@"Undo Country:%li LSN:%@",(long)pd2.currentCountryID,pd2.lsn];
}
这是数据模型
//
// LBYPlayerData.h
#import <Foundation/Foundation.h>
@interface LBYPlayerData : NSObject
@property (nonatomic,readonly) BOOL isNewGame;
@property (nonatomic) NSInteger playerID;
@property (nonatomic) NSInteger usCardIdx;
@property (nonatomic) NSInteger drawDeckIdx;
@property (nonatomic) NSInteger discardDeckIdx;
@property (nonatomic) NSInteger removeDeckIdx;
@property (nonatomic) NSInteger currentCountryID;
@property (nonatomic) NSString* lsn;
@property (nonatomic) NSString* build;
@end
//
// LBYPlayerData.m
#import "LBYPlayerData.h"
@implementation LBYPlayerData
-(id)init
{
self = [super init];
_isNewGame = YES;
return self;
}
-(void)encodeWithCoder:(NSCoder *)aCoder
{
// NSLog(@"Saving Player Data");
_isNewGame = NO;
[aCoder encodeBool:_isNewGame forKey: NSStringFromSelector(@selector(isNewGame))];
[aCoder encodeInt64:_playerID forKey: NSStringFromSelector(@selector(playerID))];
[aCoder encodeInt64:_usCardIdx forKey: NSStringFromSelector(@selector(usCardIdx))];
[aCoder encodeInt64:_drawDeckIdx forKey: NSStringFromSelector(@selector(drawDeckIdx))];
[aCoder encodeInt64:_discardDeckIdx forKey: NSStringFromSelector(@selector(discardDeckIdx))];
[aCoder encodeInt64:_removeDeckIdx forKey: NSStringFromSelector(@selector(removeDeckIdx))];
[aCoder encodeInt64:_currentCountryID forKey: NSStringFromSelector(@selector(currentCountryID))];
[aCoder encodeObject:_lsn forKey: NSStringFromSelector(@selector(lsn))];
[aCoder encodeObject:_build forKey: NSStringFromSelector(@selector(build))];
// NSLog(@"Current Counry: %li",(long)_currentCountryID);
}
-(id)initWithCoder:(NSCoder *)aDecoder
{
// NSLog(@"Loading Player Data");
self = [self init];
if (self) {
_isNewGame =[aDecoder decodeBoolForKey:NSStringFromSelector(@selector(isNewGame))];
[self setPlayerID :[aDecoder decodeIntegerForKey:NSStringFromSelector(@selector(playerID))]];
[self setUsCardIdx :[aDecoder decodeIntegerForKey:NSStringFromSelector(@selector(usCardIdx))]];
[self setDrawDeckIdx :[aDecoder decodeIntegerForKey:NSStringFromSelector(@selector(drawDeckIdx))]];
[self setDiscardDeckIdx :[aDecoder decodeIntegerForKey:NSStringFromSelector(@selector(discardDeckIdx))]];
[self setRemoveDeckIdx :[aDecoder decodeIntegerForKey:NSStringFromSelector(@selector(removeDeckIdx))]];
[self setCurrentCountryID:[aDecoder decodeIntegerForKey:NSStringFromSelector(@selector(currentCountryID))]];
[self setLsn :[aDecoder decodeObjectForKey :NSStringFromSelector(@selector(lsn))]];
[self setBuild :[aDecoder decodeObjectForKey :NSStringFromSelector(@selector(build))]];
}
return self;
}
@end
答案 0 :(得分:0)
问题在于NSAssert。我发现在NSAssert语句中调用函数来存档对象的代码。