3

に配列を保存しようとしていNSUserDefaultsます。エンコーダーとデコーダーを使用する必要があることを読みましたが、それでも同じエラーが発生します

*** -[NSUserDefaults setObject:forKey:]: Attempt to insert non-property value '(
    "<Item: 0x1e86e380>",
    "<Item: 0x1e86fd60>",
    "<Item: 0x1e86fda0>",
    "<Item: 0x1e86fde0>",
    "<Item: 0x1e86fe10>"
)' of class '__NSArrayM'.  Note that dictionaries and arrays in property lists must also contain only property values.
[unknown][unknown][unknown][unknown][unknown](gdb) 

どうして??

これが私のコードです:

これは私のモデルです。NSStringsNSNumbersおよびNSMutableArrays: _

- (void)encodeWithCoder:(NSCoder *)encoder
{
    [encoder encodeObject: self.title forKey:@"title"];
    [encoder encodeObject: self.desc forKey:@"desc"];
    [encoder encodeObject: (NSNumber*) self.day forKey:@"day"];
    [encoder encodeObject: self.images forKey:@"images"];
}

- (id)initWithCoder:(NSCoder *)decoder
{
    self = [super init];
    if( self != nil )
    {
        self.title = [decoder decodeObjectForKey: @"title"];
        self.desc = [decoder decodeObjectForKey: @"desc"];
        self.day = [decoder decodeObjectForKey: @"day"];
        self.images = [decoder decodeObjectForKey: @"images"];

    }
    return self;
}

これは AppDelegate のDidFinishLaunchingメソッドにあります。

if([[NSUserDefaults standardUserDefaults] objectForKey:@"savedData"] == nil)
{
    items = [[NSMutableArray alloc] init];

    NSString *filePath = [[NSBundle mainBundle] pathForResource:@"items" ofType:@"json"];
    NSString *contents = [NSString stringWithContentsOfFile: filePath  encoding: NSUTF8StringEncoding error: nil];
    SBJsonParser *jsonParser = [[SBJsonParser alloc] init];
    NSMutableDictionary *json = [jsonParser objectWithString: contents];
    jsonParser = nil;
    items = json[@"item"];

    for(NSDictionary *itemDict in items)
    {

        Item *item = [[Item alloc] init];

        item.title = [itemDict valueForKey:@"title"];
        item.desc = [itemDict valueForKey:@"description"];
        item.day = [itemDict valueForKey:@"day"];
        item.images = [itemDict valueForKey: @"images"];

        [items addObject: item];

    }    
}
else
{

    NSData *decodedObject = [userDefault objectForKey: [NSString stringWithFormat:@"savedData"]];
    NSArray *decodedArray =[NSKeyedUnarchiver unarchiveObjectWithData: decodedObject];


    items = [decodedArray mutableCopy];

}

そして、これは私が持っていAppWillTerminateます:

   userDefault = [NSUserDefaults standardUserDefaults];
   NSData *encodedObject = [NSKeyedArchiver archivedDataWithRootObject: items];
   [userDefault setObject: encodedObject forKey:[NSString stringWithFormat:@"savedData"]];
4

1 に答える 1

1

序文: ユーザーのデフォルトは汎用データベースではないことを理解してください。そこに保存することを提案しているデータが非常に小さい場合を除き、これを行うことは強くお勧めしません. もう 1 つの方法は、Application Support ディレクトリなど、明確に定義された場所にデータを格納することです。

編集

前の段落で、Application Support ディレクトリは変更されるデータに使用すべきではないと述べました。これをサポートするものは何も見つかりません。Apple 自身のドキュメントには、「アプリをサポートするが、アプリの実行に必要ではない任意の種類のファイルをアプリが保存する場所」であり、ユーザー データはそこに保存されるべきではなく、各アプリは独自のファイルを作成して維持する必要があると記載されています。最上位に書き込むのではなく、その中のディレクトリ。このフィクションをどこで手に入れたのか定かではありません。

編集終了

そうは言っても、コンパイラが「非プロパティ値」について不平を言うとき、それは、NSArray, NSDictionary, NSString, NSData, NSDateまたはではない何かを書き込もうとしていることを意味しますNSNumber.

あなた自身のオブジェクトが NSKeyedArchiver と NSKeyedUnarchiver を利用する必要があることは正しいです。しかしNSCoding、モデル オブジェクトにメソッドを実装しているからといって、それがプロパティ リストの値ではないという事実は変わりません。

あなたがする必要があるのは、各オブジェクトを保存しようとするNSKeyedArchiver 前に使用することです。NSDataこれにより、プロパティ リスト オブジェクトとして格納できるのインスタンスが生成されます。

于 2013-04-23T13:24:02.927 に答える