Extracting value from NSDictionary with brackets vs. objectForKey: or valueForKey:
Asked Answered
F

2

5

I was wondering what this convenience method stood for but was unable to find any answers for it.

What exactly does theDictionary[@"key"] do when wanting to extract a value from a dictionary? Is it using valueForKey: or objectForKey:?

What is better performance wise? Is it better to write the whole message like [theDictionary objectForKey:@"key"] or is the convenience method sufficient?

Flintshire answered 23/6, 2016 at 18:1 Comment(1)
Accessing keys in NSDictionary using key notationAuthentic
E
4

Let's have that in a context:

There are different ways to access an object that is accessable by a key.

A. Key-Value Coding

Key-value coding is done with -valueForKey: et al. Since this is implemented in NSObject nearly all objects having properties (have properties accessible by key) response to this. Basically this methods forms a selector from the key and sends it to the object. Beside this you have the ability to build key path and there are some special keys, i. e. count.

This is completely implemented outside the compiler.

Instances of NSDictionary supports this.

B. Subscripting

[] is the syntax for subscripting. If the key between [ and ] is an object, it is keyed subscripting. The compiler transforms that syntax into a -objectForKeyedSubscript: et al. message. The receiver has to implement the methods.

Instances of NSDictionary supports this by simply sending -objectForKey: et al. to self. But there is a little difference, see below.

C. NSDictionary

Additionally NSDictionary implements -objectForKey:.

There is no right or wrong. Personally I would prefer the most specific message for instances of NSDictionary, -objectForKey: et al. However, keyed subscription might be better readable.

Key-value coding is good, if you do not know the type of the receiver.

BTW: Key-value coding and keyed subscripting let's you set nil values in an instance of NSMutableDictionary, while -setObject:forKey: et al. forbids that.

Endo answered 23/6, 2016 at 18:25 Comment(0)
S
3

NSDictionary provides the method objectForKey: to access its contents. The difference to valueForKey: is explained in depth in this related question: Difference between objectForKey and valueForKey?.

The [] operator is a shortcut to objectForKey:. Whichever you use doesn't really matter, but the former one is easier to read (less code noise), instantly clear in its intention, and you don't have to think about whether it's objectForKey: or valueForKey:.

So personally, I much prefer [].

Slather answered 23/6, 2016 at 18:11 Comment(5)
The subscripting is sugar for objectForKeyedSubscript:, not objectForKey: directly. (Also, @[] is a literal NSArray, not a subscript: remove the @.)Authentic
@JoshCaswell Yes, surely without the (copied) ´@´. Doesn't it ultimately call through to ´objectForKey:´? Or does the ´objectForKeyedSubscript:´ indirection have some side effects?Slather
Correct, on NSDictionary, it just calls straight through to objectForKey:.Authentic
It has side effects for the setter in a mutable dictionary: nil is allowed. Even this is no explicit part of the Q, one should say that.Endo
dict[key] = value actually translates to setObject:forKeyedSubscript, which has the behavior of calling removeObjectForKey if the value is nil. That what gives you the ability to remove objects by assigning nil to a key.Fontanel

© 2022 - 2024 — McMap. All rights reserved.