2012-07-11 51 views
6

在NSMutableDicitionary的setValue方法中,forKey和forKeyPath有什么区别?我在文档中查找了两个,他们对我来说看起来是一样的。我尝试了以下代码,但我无法区分差异。Objective-C:forKey和forKeyPath有什么区别?

NSMutableDictionary *dict = [NSMutableDictionary dictionary]; 
[dict setValue:@"abc" forKey:@"ABC"]; 
[dict setValue:@"123" forKeyPath:@"xyz"]; 
for (NSString* key in dict) { 
    id val = [dict objectForKey:key]; 
    NSLog(@"%@, %@", key, val); 
} 
+2

仅当您使用更复杂的字典(具有多个级别)时才会有所不同。你看起来相同的原因是只有一个关键路径(没有'.'表示一个额外的路径组件)实际上只是一个关键。 – Dustin 2012-07-11 13:41:46

回答

7

这两种方法都是Key-Value Coding部分和一般不应被用于在词典中元素的访问。它们只能用于NSString类型的密钥,并且需要特定的语法。

两者之间的区别在于指定一个(单个)键只会查找该项目。

另一方面指定关键路径遵循对象的路径。如果您有字典词典,则可以使用"key1.key2"这样的关键路径查找第二级元素。

如果您只想访问字典中的元素,则应使用objectForKey:setObject:forKey:

编辑回答为什么valueForKey:不应使用:

  1. valueForKey:仅适用于字符串键。字典可以使用其他对象作为键。
  2. valueForKey:以不同的方式处理以“@”字符开头的键。您无法访问其密钥以@开头的元素。
  3. 最重要的是:通过使用valueForKey:你说:“我正在使用KVC”。应该有这样做的理由。当使用objectForKey:时,您只需通过自然的预期API访问字典中的元素。
+0

出于好奇,'valueForKey:'不应该用于字典的原因是什么? – Monolo 2012-07-11 13:50:45

+0

@Monolo见编辑。 – 2012-07-11 14:46:00

3

苹果文档:NSKeyValueCoding Protocol Reference

的setValue:forKey:

设置由给定键到给定值所指定的接收器的性能。

实施例:

[foo setValue:@"blah blah" forKey:@"stringOnFoo"]; 

的setValue:forKeyPath:

设置由给定值的给定的键路径标识的属性的值。

实施例:

[foo setValue:@"The quick brown fox" forKeyPath:@"bar.stringOnBar"]; 
+1

另外,使用“setValue:forKeyPath:”时,请确保keyPath上的对象存在。如果它为零,则该方法将因为路径不完整而悄然失败。 – ezekielDFM 2012-07-11 13:50:01

1

keyPath可用于遍历任意对象路径,只要它们实现了NSKeyValueCoding即可。他们不需要是NSDictionary s。例如:

NSString *departmentName = [self valueForKeyPath:@"[person.department.name"]; 

虽然这是一个有点人为的例子。