0:00
[MUSIC]
A really powerful data structure that you have available to
you in programming with Objective-C is the NSDictionary.
It's hard to explain the NSDictionary to someone that's never
used something like this.
They go by different names in other programming languages.
Sometimes they're called associative arrays,
sometimes they're called dictionaries like they are in Objective-C, and
sometimes they're called maps, like for example in Java.
0:32
And what they are, at a high level,
is a data structure that allows you to keep track of key value pairs.
And it's kind of like combining a set within array.
And what you're gonna do is you're gonna have a bunch of pairs that are kept track
of in your dictionary object, and the keys are the first element of the pair,
and the values are the second element of the pair.
And so, we're gonna put them together, so that each element from a set,
which is the keys, is gonna match with an element from an array, but
you're gonna access them as pairs rather than through a list or a set,
which what's similar about it is that, the keys have to be unique.
NSDictionary is immutable.
We're looking at a bunch of immutable data structures, and that means that once you
create the dictionary, you can't change it without making a copy of it, and
that can have implication for memory management.
1:26
If you wanna know the definitive list of all of the ways in which you can use it,
the methods that are available, possibly any changes that happened to NSDictionary,
make sure you do either web search for NSDictionary documentation, and you'll
find the developer.apple.com website should come up very high in the list.
That's the definitive location for information about the dictionary.
If you need help on a method or some other information.
One of the first things you're probably gonna wanna do with a dictionary is to
create one.
And a dictionary is one of the Objects,
with which you can use the @ literal notation.
So if you use at, and
then you put curly braces after it, that is an indication to bundle the data
that follows the at curly braces into an NSDictionary object by Objective-C.
And so, in this case,
what we have is we have an example of a dictionary created called dinnerRequests.
We have a whole bunch of different NSStrings in there, and
you can see they're separated by a colon, and then the end of the line has a comma.
And so, what that is, is it's a sequence of key and value pairs.
And they're matched one to the other around the colon.
So Don's matched with tofurkey, Sandy's matched with burrito, Julius'
matched with chicken, Theo's matched with hamburger, Joy is matched with burrito,
Martha is matched with pixy sticks, and Coconut is matched with kibble.
2:45
Now, in this example we're using all strings, both for our keys and our values.
And that doesn't have to be the case.
You can use any object pointer you want, for either the key or the value.
Typically, keys are pretty commonly used.
NSStrings are typically used for keys, although not always,
it's a very common case to use NSStrings for the keys.
But the values are often very different kinds of objects depending on what your
application is.
They can be a object within an object too.
So your value could be a set, your value could be another dictionary,
your value could be a number.
Or it could be any number of different things.
So in this example, when we go and we output that NSDictionary, you can see
we're not iterating through it, we're just directly calling the description method on
the dinnerRequest object via the format token percent app.
And when we do that, the NSDictionary
turns it's contents into a string, and it looks like that.
The part of the string that it puts out is the curly braces as well.
And you can see that it said Coconut = kibble,
Don = tofurkey, Joy = burrito, etc, etc.
And one thing you can see here is that a NSDictionary's not ordered.
So in that sense, it's like a set, because although you have a lot of pairs and
the pairs have a tight grasp with each other,
the order in which those pairs come out of a dictionary is not guaranteed at all.
4:07
The other thing, I don't know if it's clear or
not from this example, but the keys have to be unique.
If you try and put a key into NSDictionary a second time,
regardless of what its value is.
The first key will be overridden.
Or you'll get an error, depending on the situation.
So it's okay to have multiple values, though.
So in this example, you can see that both Sandy and Joy are matched with burrito.
But that's a value, and the value can be repeated.
4:37
So this is a different way of creating an NSDictionary, not just the literal value
with the at symbol and the curly braces, but also a call to the class NSDictionary.
With the message dictionary with objects and keys.
So something to be careful about here is that, this is just a long list.
There's no colons in this list, and so
you have to remember to alternate between one thing and the other thing.
And the other thing is that the object comes first and the key comes second.
Now, in my mind that's a little confusing,
because in the dictionary you look things up with keys.
And it kinda matches better with the literal curly brace notation
to put the key first, but that's not what you do.
And it's actually consistent with the name of this method which is Dictionary with
Objects and Keys not Keys and Objects.
The last thing to be aware is that it's a nil-terminated list
when you create your dictionary in this way.
And then, when you output it, although the keys and
values are alternates in the list as I said.
And when you output it you see something very similar to what we had before,
the same dictionary gets created.
5:40
There's one last way that's worth noting about how you can create a dictionary, and
that's using a combination of two arrays and mapping them together.
So in this case, I created one array called people and
that has, an array is an ordered list with possible duplicates.
So it's Don, Sandy, Julius, Theo, Joy, Martha, Coconut.
And then, the second array is requests.
And this is also an array.
And it says tofurkey, burrito, chicken, hamburger, burrito, pixie sticks, kibble.
So you can see there's a double there.
But that's okay, cuz it's an array.
And now, we're gonna create a dictionary out of that.
We're gonna create a dictionary by using the method dictionary with objects and
four keys.
As a method that's being called on the NSDictionary class.
And so, we're gonna pass it the requests for the objects and the keys for people.
And the output that we get is what we would expect,
same thing that we had before, we're constructing the same dictionary over and
over again in different ways.
I actually don't really like this style of creating a dictionary, and
the reason why is twofold.
It's kinda confusing for me.
Like the previous one, in this case, you specify your objects first, and
then your keys.
That's a little bit counterintuitive to me,
because when you find the data in a dictionary, you look it up by the key.
The more troubling thing that I have with this approach is that,
what you create the dictionary with is actually two arrays.
And that's not really appropriate, because the keys act as a set.
If you have a duplicate at array that you passed into four keys,
you're gonna get behavior that you probably weren't expecting,
because you shouldn't have duplicates.
In an ideal world, four keys would fill would be past a set.
But then, the problem is that sets aren't ordered, and
so if you were gonna match each element of the keys up with one element of the array
you would have to sue something that is ordered.
So this is sort of a hacky halfway way of developing a dictionary.
7:51
The first one says, if you have an at symbol followed by a number,
what kind of object are you gonna create?
The second one says, if you have an at symbol followed by quotes and
with text in it, what are you gonna create?
The third question is, if you have an at symbol with square brackets and
a sequence of objects, what are you gonna create?
And the fourth one is, if you have an at symbol with curly braces and
object colon object comma object colon object, what are you gonna create?
Four different ways that you can use the at symbol to create literal objects.
Pause the video if you need to, we'll give you the answers in a moment.
Last chance.
8:27
Okay, so the first one creates an NSNumber.
That is an object oriented way of representing
a primitive number like int or float.
The next one is the NSString.
That's an object-oriented way of representing a char star, a string.
The third one is a NSArray.
This is also an object-oriented way of representing an array,
which is also available to you in C, but with different syntax.
And then, the third thing is an object-oriented way of creating
a dictionary.
And although it's probably possible to have a dictionary in C,
I don't think there is a primitive dictionary in C.
9:15
One thing that you can do with it is you can select objects from it, and
there are lots of different ways that you can select an objects from a dictionary,
it's kind of intuitive actually.
So in our first line here we are creating our dictionary and
we are using the literal notation.
A sequence of
people followed by a sequence of things that they would like for dinner.
9:33
In the first line, we use an NSLog statement with a format token of
percent at to ask what does Theo want for dinner?
And the way we find that out is we use the variable name dinnerRequests.
We use square bracket notation, and
instead of using an index like a number that we would have used when it was
in NSArray, instead of asking with a number, we're gonna ask with a key.
So it doesn't have to be a number,
it could be anything that could be a possible key in your dictionary.
10:03
And if that key is present in your dictionary,
then the value will be returned.
And so, in this case, we hope that gets returned.
In our second line, we're gonna access our values in another way.
We're gonna use a method called object for key.
10:43
We do a reverse look-up.
So instead of asking for a value associated with a key,
we're gonna ask for all of the keys associated with a particular value.
Now, we know that there can only be one unique key of a,
dictionary only has unique keys, they can't be repeated, but
the keys can have the same value repeated over and over again.
So it's possible,
like in our dictionary here, that the burrito has showed up twice.
And so if you wanna know all of the keys that are associated with that object,
you can do the message all KeysForObject.
We're gonna pass that into a local variable that we're calling
burritowanters.
And then, we're going to output that.
We're gonna say these are the burrito wanters.
We're gonna do a fast enumeration through that array.
And each element of the array, we're gonna pass the description method to see
which key was associated with that value.
First one is almost the exact same id as an array selector.
11:44
And the third one is really a reverse look-up.
Typically, you don't do it in that order.
And then, the output that you get, as we hope for, at least we hope this is what we
get, the burrito wanters is an array of keys that we're cycling through.
And we see that Theo wants hamburger for dinner.
Good. That was our look-up.
That's what we wanted.
Joy wants burrito for dinner.
That's good. That was our look-up.
It's what we wanted.
And then, these are the burrito requests, coming from Sandy and Joy.
Yep, great, so we've got all the keys associated with the value burrito.
Okay, terrific.
So that's a way of selecting things from the NSDictionary class.
12:18
Now, if want to cycle through all the elements in the dictionary,
if you want to iterate through them, you can do a fast enumeration.
But it's important to realize that if you do just a straightforward enumeration like
this for id k in dinnerRequests, what k is going to be set equal
to in each iteration through that loop is one of the keys in your dictionary.
So k, because getting the related value's really simple, but
that is the way in which you index into a dictionary, and so that kinda makes sense.
So in this case, we go through each one of the keys intern within the iterator,
and we output using a parenthesis and
a comma in the text just to demonstrate that we are doing it a different way.
13:12
Another way you can go through your NSDictionary is by values.
And this is unusual, because dictionaries are really about looking up keys.
But you can create an array of all the values that are in your Dictionary.
So in this case, we pass dinnerRequests the message allValues, and
v is gonna be a fast enumerator that goes through each one of the values.
And then one by one, we're gonna print out which value we got through our iteration,
and we're gonna ask how many Ts are associated with that value.
We're gonna output that.
13:49
And the result is this, that we find our that burrito is requested by two.
Chicken, pixie sticks and tofurkey is requested by one.
Burrito gets, because this is an array that you get back from all values,
we hit burrito twice, and so we ask burrito again.
We hit burrito once with Sandy then we hit burrito once when it's in there for Joy.
And then, we output kibble and hamburger.
Now, if you find yourself looping through values in a dictionary often,
it's probably the case that you're not using the right data structure.
14:30
You can also compare dictionaries.
In order to be equal,
two dictionaries have to have key sets that are equal for starters.
The order doesn't matter, but the size and the content do.
So not only must the have the same number of keys, those keys must all be the same.
The key also has to have a value that's equal in both of the dictionaries.
So dictionary one and dictionary two here, they have to have the white dots represent
the keys, and the orange dots represent the values, and
they both have to have the same number of keys.
The keys have to have the same value, and each of those keys
with one value has to be mapped to a value with an equivalent value.
I'm overloading the word value, sorry.
15:25
And these keys are used like an index.
The dictionary itself is used like an index.
It's to keep track of a bunch of different things you might wanna look up
that's associated with a given key.
So we use the key to ask what is the data associated with the value, with the key.
In an example, might be if you're keeping track of a budget user accounts,
you might have the idea of the user be the key, and
then you might have a custom object be the value.
So that you can ask what is the data associated with user id 12345, and
get back an object that has the name, the birth date,
any records that you have associated with them.
It's a very common way to use a dictionary.