1

NSDictionaryをに保存してからNSUserDefaults取得すると、に変換されるという奇妙な問題が発生していNSCFStringます。

ここにデータを保存します。

- (void)saveProgress
{
    // Save our progress to the user defaults.
    NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
    NSMutableDictionary *progressDict = [NSMutableDictionary dictionary];
    if ([defaults objectForKey:@"session_progress"] != nil) {
        [progressDict addEntriesFromDictionary:[defaults dictionaryForKey:@"session_progress"]];
    }
    NSMutableDictionary *targetsDict = [NSMutableDictionary dictionary];
    if ([progressDict objectForKey:@"targets"] != nil) {
        [targetsDict addEntriesFromDictionary:[progressDict objectForKey:@"targets"]];
    }
    NSMutableDictionary *trackableDict = [NSMutableDictionary dictionary];
    if ([targetsDict objectForKey:@"mda_sao_ext_04"]) {
        [trackableDict addEntriesFromDictionary:[targetsDict objectForKey:@"mda_sao_ext_04"]];
    }
    [trackableDict setObject:[NSNumber numberWithBool:YES]
                      forKey:@"viewed"];
    NSLog(@"SAVE Trackable %@ %@", [trackableDict class], trackableDict);
    [targetsDict setObject:trackableDict
                    forKey:@"mda_sao_ext_04"];
    NSLog(@"SAVE Targets %@ %@", [targetsDict class], targetsDict);
    [progressDict setObject:targetsDict
                     forKey:@"targets"];
    [defaults setObject:progressDict
                 forKey:@"session_progress"];
    [defaults synchronize];
}

そして、ここにデータをロードします:

- (NSInteger)loadProgress
{
    // Load our progress from the user defaults.
    NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
    if ([defaults objectForKey:@"session_progress"] == nil) {
        return 0;
    }
    NSDictionary *progressDict = [defaults dictionaryForKey:@"session_progress"];
    if ([progressDict objectForKey:@"targets"] == nil) {
        return 0;
    }
    NSDictionary *targetsDict = [progressDict objectForKey:@"targets"];
    NSLog(@"LOAD Targets %@ %@", [targetsDict class], targetsDict);
    NSInteger viewedCount = 0;
    for (NSDictionary *trackableDict in targetsDict) {
        NSLog(@"LOAD Trackable %@ %@", [trackableDict class], trackableDict);
        if ([[trackableDict objectForKey:@"viewed"] boolValue]) {
            ++viewedCount;
        }
    }

    return viewedCount;
}

アプリがでクラッシュしloadProgressます。コンソールへの出力は次のとおりです。

LOAD Targets __NSCFDictionary {
    "mda_sao_ext_04" =     {
        scanned = 1;
        viewed = 1;
    };
} 
LOAD Trackable __NSCFString mda_sao_ext_04

最初のトレースから、 `mda_sao_ext_04は辞書であることがわかりますが、何らかの理由で文字列に変換されます。

何かアイデアや提案はありますか?ありがとう!

4

2 に答える 2

5

NSDictionaryの高速列挙は、値ではなくキーを返します。

for (NSDictionary *trackableDict in targetsDict) {

ここでは、すべてのキーをループします。変化する

NSLog(@"LOAD Trackable %@ %@", [trackableDict class], trackableDict);

NSLog(@"LOAD Trackable %@ %@", [trackableDict class], targetsDict[trackableDict]);
于 2013-02-11T22:23:43.640 に答える
4
for (NSDictionary *trackableDict in targetsDict)

このfor構造は、値ではなくキーを繰り返し処理します。したがって、価値を得るには、次のいずれかを行う必要があります

for (NSDictionary *trackableDict in [targetsDict allValues])

また

for (NSString *trackableKey in targetsDict)
{
    NSDictionary *trackableDict = targetsDict[trackableKey];
    .....
}
于 2013-02-11T22:21:54.310 に答える