在NSMutableDictionary中使用setObject时出错

时间:2012-01-04 00:52:15

标签: objective-c ios5 nsmutabledictionary

我得到了例外:

  

- [__ NSCFDictionary setObject:forKey:]:发送到不可变对象的mutating方法'

违规行是:

[delegate.sharedData.dictFaves setObject:@"test" forKey:@"4"];

因此在MyViewController.m中初始化Delegate:

delegate = (AppDelegate *)[[UIApplication sharedApplication] delegate];

这是我在AppDelegate.h中定义委托的方式:

#import "CommonData.h"
...
@interface AppDelegate : UIResponder <UIApplicationDelegate>
{
    NSString *tempFave;
    CommonData *sharedData;
}
@property (strong, nonatomic) NSString *tempFave;
@property (strong, nonatomic) CommonData *sharedData;

sharedData在AppDelegate.m中初始化,因此:

#import "AppDelegate.h"
...
@implementation AppDelegate
@synthesize sharedData;
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    sharedData = [[CommonData alloc] init];
    return YES;
}

sharedData在CommonData.h中定义:

@interface CommonData : NSObject
{
    NSMutableDictionary *dictAffirms;
    NSMutableDictionary *dictFaves;
}
@property (nonatomic, copy) NSMutableDictionary *dictAffirms;
@property (nonatomic, copy) NSMutableDictionary *dictFaves;

共享数据实现文件CommonData.m:

#import "CommonData.h"
...
@implementation CommonData

@synthesize dictAffirms;
@synthesize dictFaves;

@end

我已声明CommonData的成员是Mutable。显然这是不够的。为了写入CommonData中的字典,我还需要做些什么?

3 个答案:

答案 0 :(得分:3)

我在尝试写入从plist填充的字典之前看到过此错误。如果你使用

yourMutableDictionary = [someDataSource objectForKey:@"someKey"];

你的字典将是不可变的,即使它被声明为可变的。改为使用

yourMutableDictionary = [someDataSource mutableArrayValueForKey:@"someKey"];

并且你的问题会消失,假设 实际上是你的问题。它可能是这样的:

yourMutableDictionary = [[NSDictionary alloc] init];

yourMutableDictionary = [NSDictionary new];

你只是意外地创建了不可变对象,这与上面的问题差不多,只是不同。

很高兴看到用于初始化NSMutableDictionaries的代码。

编辑:也许尝试这样的事情,因为我很好奇结果会是什么。而不是使用:

[delegate.sharedData.dictFaves setObject:@"test" forKey:@"4"];

NSMutableDictionary* dict = [[NSMutableDictionary alloc] initWithDictionary:delegate.sharedData.dictFaves];
[dict setObject:@"test" forKey:@"4"];
delegate.sharedData.dictFaves = dict;
[dict release];

答案 1 :(得分:1)

您已声明dictFaves是可变的,但这并不意味着您实际上存储了一个可变对象。检查初始化程序。您可能会遇到以下情况:

dictFaves = [[NSDictionary alloc] init];

如果是这样,您需要将其更改为NSMutableDictionary

答案 2 :(得分:1)

您的问题是您的字典属性设置器被声明为copy。 NSMutableDictionary的copy方法返回一个不可变的NSDictionary(通常,copy几乎总是返回一个不可变对象)。因此,假设您正在使用标准的合成setter,那么无论何时设置该属性,您都会在幕后分配错误的类型。它可能应该是strong