Pablo Englebienne wrote:
Hi, I'm trying to work with a dictionary of dictionaries and I'm having trouble accessing a specific element of it:

$ python
Python 2.6 (trunk:66714:66715M, Oct  1 2008, 18:36:04)
[GCC 4.0.1 (Apple Computer, Inc. build 5370)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
 >>> r = ('a','b','c')
 >>> c = (1,2,3)
 >>> d = dict.fromkeys(r,dict.fromkeys(c))
 >>> d

This does

d0 = dict.fromkeys(c)
d  = dict.fromkeys(r, d0)


{'a': {1: None, 2: None, 3: None}, 'c': {1: None, 2: None, 3: None}, 'b': {1: None, 2: None, 3: None}}
 >>> d['a'][1]=0
 >>> d
{'a': {1: 0, 2: None, 3: None}, 'c': {1: 0, 2: None, 3: None}, 'b': {1: 0, 2: None, 3: None}}
 >>> import copy

As you can see, attempting to assign a specific member, d['a'][1] updates all values in d[*][1], not what I intended.

The d0 value is shared between all keys of d. As a result, you get the behaviour you noticed.
(ie there is only 1 dict-value, it gets printed 3 times when you print 'd')

I thought the solution could be in using copy.deepcopy, but I might not be using it right:

 >>> d2 = dict.fromkeys(r,copy.deepcopy(dict.fromkeys(c)))

Here you do

d0 = dict.fromkeys(c)
d1 = copy.deepcopy(d0)
d2 = dict.fromkeys(r, d1)

d0 and d1 are completely seperate due to the deepcopy(), but the last line still uses the same d1 value for all its keys, as in your first attempt. for this reason, the problem does not disappear.


Any suggestions/pointers would be appreciated!

To solve this, you need to construct a fresh value for each key.

You can do this with an iterator and a dictionary constructor:

>>> c = (1,2,3)
>>> r = ('a','b','c')
>>> d3 = dict(( (rv, dict.fromkeys(c)) for rv in r ))

d3 is created by constructing a dict from a list of tuples (key, val), where the key rv is from your 'r' tuple, and val is constructed anew each time from 'c'.

>>> d3
{'a': {1: None, 2: None, 3: None}, 'c': {1: None, 2: None, 3: None}, 'b': {1: None, 2: None, 3: None}}
>>> d3['a'][1]=0
>>> d3
{'a': {1: 0, 2: None, 3: None}, 'c': {1: None, 2: None, 3: None}, 'b': {1: None, 2: None, 3: None}}

Sincerely,
Albert

_______________________________________________
Tutor maillist  -  Tutor@python.org
http://mail.python.org/mailman/listinfo/tutor

Reply via email to