NSDictionary如何处理NIL对象?

时间:2011-07-26 03:39:55

标签: objective-c ios nsdictionary

请考虑以下代码。本质上,我们得到2个字符串,然后我们将这些值添加到NSDictionary。

然而,我遇到了一个奇怪的错误。当fbAccessTokenKey为0x0(或nil)时,也不会添加twitterToken。

NSString *fbAccessTokenKey=[[UserStockInfo sharedUserStockInfo] getFBAccessTokenKey];
NSString *twitterToken=[[UserStockInfo sharedUserStockInfo] getTwitterAccessTokenKey];

NSDictionary *params= [[NSDictionary alloc] initWithObjectsAndKeys:
                       fbAccessTokenKey, @"fb_access_token", 
                       twitterToken, @"twitter_access_token", 
                       nil
                       ];

为什么会发生这种情况,解决这个问题的好方法是什么?

3 个答案:

答案 0 :(得分:14)

nil用作标记“参数结束”列表的“标记”。如果twitterToken为nil,则运行时将遍历您的参数,一旦到达twitterToken,它就会认为它是在对象和键列表的末尾。这是由于C / Obj-C在列表参数方面的实现方式。

另一种安全的方法是使用NSMutableDictionary,并检查您的值是否为非零,然后将它们添加到可变字典中,如下所示:

NSString *fbAccessTokenKey = [[UserStockInfo sharedUserStockInfo] getFBAccessTokenKey];
NSString *twitterToken = [[UserStockInfo sharedUserStockInfo] getTwitterAccessTokenKey];

NSMutableDictionary *params = [NSMutableDictionary dictionary];
if (fbAccessTokenKey) [params setObject:fbAccessTokenKey forKey:@"fb_access_token"];
if (twitterToken) [params setObject:twitterToken forKey:@"twitter_access_token"];

有关更多技术信息,有一篇关于Cocoa with Love的文章:http://cocoawithlove.com/2009/05/variable-argument-lists-in-cocoa.html

答案 1 :(得分:4)

答案 2 :(得分:2)

而不是使用initWithObjectAndKeys进行初始化。为什么不实例化NSMutableDictionary,然后添加键值对(如果键为空,则不添加)?

NSMutableDictionary * params = [[NSMutableDictionary alloc] init];

if (fbAccessTokenKey)
    [params setObject:fbAccessTokenKey forKey:@"fb_access_token];

// ... etc

如果你想让它从那时起保持不变,你可以将它转发回NSDictionary。

<强>更新

回应Josh's评论只是一个注释,我应该澄清,当然演员不会将参数NSMutableDictionary神奇地转换为NSDictionary。但是如果你把它传递给需要NSDictionary的代码,那么演员会让你这样对待它。

Josh的评论包括以下代码:

NSMutableDictionary * md = [[NSMutableDictionary alloc] init]; 
NSDictionary * d = (NSDictionary *)md; 
[d setObject:@"Yes I am" forKey:@"Still mutable?"]; 
NSLog(@"%@", d); // Prints { "Still mutable?" = Yes I am; }

这将生成以下编译器警告(对我来说,警告生成错误,编译错误):

  

file:blah.m:错误:语义问题:'NSDictionary'可能无法响应'setObject:forKey:'