Error Appending list elements to dictionary in Python

Question:

I have a weird problem when trying to append a list of elements to a dictionary. I am not sure what I am doing wrong. Any help is very much appreciated.

here is what I have:

keys = ['a', 'b', 'c']
d = dict.fromkeys(keys, [])
d['a'].append(10)
d['a'].append(11)
d['b'].append(30)
print(d)

the output I am getting is:

{'a': [10, 11, 30], 'b': [10, 11, 30], 'c': [10, 11, 30]}

I would expect:

{'a': [10, 11], 'b': [30], 'c': None}

Thank you

Asked By: RXP

||

Answers:

Does this solve your problem?

d = {'a': [], 'b': [], 'c': []}
d['a'].append(10)
d['a'].append(11)
d['b'].append(30)
print(d)
Answered By: Connor

You are providing an empty list, and fromkeys() uses this particular object for all the keys, so that their corresponding values refer to the same object. When you do d['a'].append(10), it appends 10 to this single object, which all the dict items share, thus resulting in what you are getting now.

Python document mentions this exact situation:

fromkeys() is a class method that returns a new dictionary. value defaults to None. All of the values refer to just a single instance, so it generally doesn’t make sense for value to be a mutable object such as an empty list. To get distinct values, use a dict comprehension instead.

https://docs.python.org/3/library/stdtypes.html#mapping-types-dict

Following the suggetion in the python doc, you can do d = {k: [] for k in keys} instead.

Answered By: j1-lee

This is actually an interesting question. Apparently, fromkeys assigns the same list object to all dict keys. You can see this by applying the id() function call to the values of the dict. This function gives you the memory address of the variable. In this case, you’ll get the same address for alle keys. Hence, by appending the list of one key’s list, the other lists are also appended, because it’s the same memory address aka the same list.

keys = ['a', 'b', 'c']
d = dict.fromkeys(keys, [])
d['a'].append(10)
d['a'].append(11)
d['b'].append(30)
print(id(d['a']))
print(id(d['b']))
print(id(d['c']))
print(d)

# Output
4418025728
4418025728
4418025728
{'a': [10, 11, 30], 'b': [10, 11, 30], 'c': [10, 11, 30]}
Answered By: schilli

The same list object is being referenced by each dictionary key. fromkeys() creates a new dictionary with keys and values are set to the specified value, which in this case is a single list object that is shared among the dict key items.

Try this to assign a new list to each key value of the dictionary:

keys = ['a', 'b', 'c']

d = {key: [] for key in keys}

d['a'].append(10)
d['a'].append(11)
d['b'].append(30)

print(d)

Output:

{'a': [10, 11], 'b': [30], 'c': []}
Answered By: CodeMonkey
Categories: questions Tags: ,
Answers are sorted by their score. The answer accepted by the question owner as the best is marked with
at the top-right corner.