Dictionaries and default values
Like this:
host = connectionDetails.get('host', someDefaultValue)
Is there a way to have a default value inside a dictionary in Python?
You can use a defaultdict
.
from collections import defaultdict
colors = defaultdict(lambda: (100, 100, 100))
colors["Black"] = (0, 0, 0),
colors["White"] = (255, 255, 255)
# Prints (0, 0, 0), because "Black" is mapped to (0, 0, 0) in the dictionary.
print(colors["Black"])
# Prints (100, 100, 100), because "Blue" is not a key in the dictionary.
print(colors["Blue"])
How to set default value to all keys of a dict object in python?
You can replace your old dictionary with a defaultdict
:
>>> from collections import defaultdict
>>> d = {'foo': 123, 'bar': 456}
>>> d['baz']
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
KeyError: 'baz'
>>> d = defaultdict(lambda: -1, d)
>>> d['baz']
-1
The "trick" here is that a defaultdict
can be initialized with another dict
. This means
that you preserve the existing values in your normal dict
:
>>> d['foo']
123
How does collections.defaultdict work?
Usually, a Python dictionary throws a KeyError
if you try to get an item with a key that is not currently in the dictionary. The defaultdict
in contrast will simply create any items that you try to access (provided of course they do not exist yet). To create such a "default" item, it calls the function object that you pass to the constructor (more precisely, it's an arbitrary "callable" object, which includes function and type objects). For the first example, default items are created using int()
, which will return the integer object 0
. For the second example, default items are created using list()
, which returns a new empty list object.
Python Defaultdict with defined dictionary as default value shares the same dictionary between keys
To fix this, you simply need to move your counter_format
dictionary construction into the lambda, so that a new counter_format
dictionary is created each time you try to access a missing value in your innermost defaultdict
from collections import defaultdict
userDict = defaultdict(lambda:
defaultdict(lambda: {"correct": 0, "incorrect": 0})
)
userDict['a'][1]['correct']+=1
userDict['b'][1]['correct']+=4
userDict['b'][2]['correct']+=1
print(userdict)
defaultdict(<function <lambda> at 0x7f0f6cb38550>,
{'a': defaultdict(<function <lambda>.<locals>.<lambda> at 0x7f0f679424c0>,
{1: {'correct': 1, 'incorrect': 0}}),
'b': defaultdict(<function <lambda>.<locals>.<lambda> at 0x7f0f4caaa430>,
{1: {'correct': 4, 'incorrect': 0},
2: {'correct': 1, 'incorrect': 0}})})
Python dict with default value based on key
I don't think there is a builtin way of doing this. However, instead of subclassing dict
and change getitem
, you can subclass defaultdict
itself to tell __missing__()
to call the default_factory
with an argument (the key
), rather than without args. It is still a custom class, not a builtin, but it should be quite efficient still.
from collections import defaultdict
class DefaultDict(defaultdict):
def __missing__(self, key):
return self.default_factory(key)
Then:
d = DefaultDict(lambda key: key + 5)
d[2]
# 7
How to make a list as the default value for a dictionary?
The best method is to use collections.defaultdict
with a list
default:
from collections import defaultdict
dct = defaultdict(list)
Then just use:
dct[key].append(some_value)
and the dictionary will create a new list for you if the key is not yet in the mapping. collections.defaultdict
is a subclass of dict
and otherwise behaves just like a normal dict
object.
When using a standard dict
, dict.setdefault()
correctly sets dct[key]
for you to the default, so that version should have worked just fine. You can chain that call with .append()
:
>>> dct = {}
>>> dct.setdefault('foo', []).append('bar') # returns None!
>>> dct
{'foo': ['bar']}
However, by using dct[key] = dct.get(...).append()
you replace the value for dct[key]
with the output of .append()
, which is None
.
Related Topics
How to Specify New Lines on Python, When Writing on Files
Extract Text from Xml Documents in Python
How to Make a Cross-Module Variable
In Matplotlib, What Does the Argument Mean in Fig.Add_Subplot(111)
Python Glob Multiple Filetypes
Automatically Create Requirements.Txt
Is There a Decorator to Simply Cache Function Return Values
Differences Between 'Input' and 'Raw_Input'
Find Column Whose Name Contains a Specific String
How to Check If a Process Is Still Running Using Python on Linux
Python and Regular Expression with Unicode
Converting Int to Bytes in Python 3
What's the How to Install Pip, Virtualenv, and Distribute for Python