Learn

There is another way to store dictionaries or other mappings in Python. We have looked at the defaultdict and OrderedDict so far and they handle a lot of situations so what else could we possibly need?

Well, the ChainMap container allows us to store many mappings in an ordered group, but lookups (accessing the value using a key) are repeated for every mapping inside of the ChainMap until something is found or the end is reached. If we try to modify the data in any way, then only the first mapping in the ChainMap will receive the changes. When accessing data, one way to think of the ChainMap is that it treats all of the stored dictionaries as one large dictionary, where if there are repeated keys, then the first found result is returned. Let’s see what this looks like with an example using a customer’s clothing dimensions!

First, we import the ChainMap container and set up our data.

from collections import ChainMap customer_info = {'name': 'Dmitri Buyer', 'age': '31', 'address': '123 Python Lane', 'phone_number': '5552930183'} shirt_dimensions = {'shoulder': 20, 'chest': 42, 'torso_length': 29} pants_dimensions = {'waist': 36, 'leg_length': 42.5, 'hip': 21.5, 'thigh': 25, 'bottom': 18}

Next, we initialize a ChainMap with the mappings which we want to use. In this case, the mappings are the dimensions dictionaries.

customer_data = ChainMap(customer_info, shirt_dimensions, pants_dimensions)

Now we can access values from any of the stored mappings.

customer_leg_length = customer_data['leg_length']

The parents property skips the first mapping and returns everything else (all of the parents of the first mapping).

customer_size_data = customer_data.parents

We can directly modify the data only in the first dictionary.

customer_data['address'] = '456 ChainMap Drive'

Note: In order to modify data from dictionaries which are deeper in the ChainMap, we will need to iterate through the dictionaries which are stored inside of it.

As we can see in this example, we create a new ChainMap using three different dictionaries. This allows us to access any of the key:value pairs stored inside.

Another interesting concept that the ChainMap uses is the concept of a parent mappings. If we use the .parents property, all mappings except the first one will be returned. This is because those mappings are considered to be the parent mappings to the first one. You can add a new “child” mapping to the front of the list of mappings using the .new_child() method.

To find out more about this container, check out the Python Documentation.

Now let’s use a ChainMap to keep track of our clothes business profits for the last 12 months!

Instructions

1.

Our business has been doing well over the past year and we have been provided with a list of dictionaries representing the amount of profit per month as well as additional profit from holidays when applicable. We want an easy way to monitor our profit over the most recent 12 month period. To do this, we can use the ChainMap class. This will allow us to conserve historical data while also allowing us to retrieve the most recent data. It will even allow us to work with additional keys within dictionary updates.

First, remember to import ChainMap. Then create a new ChainMap called profit_map using the year_profit_data list. Remember that a ChainMap accepts a variable number of arguments so we need to expand the list (*) so the constructor will read them as individual arguments instead of one single argument.

2.

For the next step, we need logic which will be able to calculate the normal profits and the holiday profits separately. Create a function called get_profits which calculates the sum of the standard profits (keys not containing 'holiday') and the holiday profits (keys containing 'holiday') in two different variables. Make this function return the two variables: the standard profit first and the holiday profit second. Additionally, call the function using the profit_map and store the results in variables called last_year_standard_profit and last_year_holiday_profit.

3.

It has been three months and our accountant has sent three more months worth of profit data in the form of a list of dictionaries called new_months_data. Add the new mappings to the profit_map so that the old January - March months are still in the ChainMap, but accessing those keys will return data for the most recent three months. Call the get_profits function on the profit_map again and store the results in current_year_standard_profit and current_year_holiday_profit to calculate the sum of the most recent 12 months of profit data.

4.

Finally, we want to take a look at the difference in the last 12 month period compared to the current 12 month period. Calculate the difference for the standard and holiday profits and store them in variables called year_diff_standard_profit and year_diff_holiday_profit. Print out the results to see the difference in profit for the current 12 month period.

Sign up to start coding

By signing up for Codecademy, you agree to Codecademy's Terms of Service & Privacy Policy.
Already have an account?