Understanding shallow copies

To understand shallow copies, you need to know something about how Python stores information. When you give a name to an object such as a list that stores some values, Python creates a reference (the name) to that object (the stored values).

Now, say you create a dictionary that contains this list:

>>> mydict = {'mynumber': 1, 'alist': mylist, 'mytuple': (1,2)}

If you look at the dict, it looks like the values stored in the list are stored in the dict, too:

{'mytuple': (1, 2), 'alist': ['my', 'list'], 'mynumber': 1}

But in fact the dictionary is not storing the actual values stored in the list. It is only storing the reference to the list.

That means, if you change the list...

... your dict also changes.

{'mytuple': (1, 2), 'alist': ['my', 'list', 'changed'], 'mynumber': 1}

When you make a shallow copy of something, you copy only the references, not the actual values that the references point to. So if you make a copy of a dict by using the copy() method, the copy reflects any changes made to the list that the dictionary is referring to.

>>> mycopy = mydict.copy() >>> mycopy

{'mytuple': (1, 2), 'alist': ['my', 'list', 'changed'], 'mynumber': 1}

To make a copy of the actual values so that these changes don't occur, import the copy module and use the deepcopy() function. See Chapter 8.

The standard use for setdefault() is for adding a list (or other mutable data type) to the dict and appending items to the list. Here's how the syntax looks:

mydict.setdefault(key, []).append(value)

Here's what happens:

1. If the key isn't in the dict, Python adds the key and uses an empty list as the value. Then it appends the value you specified to the list.

2. If the key is in the dict, Python tries to append your value to that key's value. (For this to work, the value must be a list because the append() method works only with lists.)

REMEMBER If you don't specify a value, the value None is used.

The following code creates a key, 13, and pairs it with a value of an empty list. Then it appends the string 'complaints' to the list:

>>> rooms = {'12A': ['argument clinic'], 12: ['abuse']} >>> rooms.setdefault(13, []).append('complaints') >>> rooms

{'12A': ['argument clinic'], 12: ['abuse'], 13: ['complaints']} The following code appends the string 'don't bother' to the list that has the key 13.

>>> rooms.setdefault(13, []).append("don't bother") >>> rooms

{'12A': ['argument clinic'], 12: ['abuse'], 13: ['complaints', "don't bother"]}

The following syntax does the same thing with a set.

mydict.setdefault(key, sets.Set()).add(value)

Was this article helpful?

0 0

Post a comment