2.0
addict now no longer adds keys when you peek on items! ☄️
This means that it's functionality now differs from defaultdict
, where calls to getitem
will produce a new entry in the defaultdict
. Hence, the following now happens when you peek on an empty key:
from addict import Dict
>>> a = Dict()
>>> a.a
{}
>>> a
{}
However, calls to setitem
works just like before:
>>> a.a = 2
>>> a
{'a': 2}
This is possible because of a new implementation detail. Calls to getitem
now still returns a new addict Dict
, but this instance have to special keyword arguments __parent
and __key
supplied to __init__
. The __parent
argument is meant to hold a reference to the Dict
in which we called getitem
, and the __key
argument refers to the key we were peeking on. When, or rather if, this new Dict
instance's setitem
method is called, it will also call setitem on it's __parent
with the key __key
and the value itself. Let me illustrate with an example.
>>> a = Dict()
>>> b = a.b
>>> a
{}
>>> b
{}
Above, both a
and b
are empty Dicts
. But let's see what happens to a
when we set an item on b
>>> b.c = 2
>>> b
{'c': 2}
>>> a
{'b': {'c': 2}}
Magic.
You should consider these arguments to __init__
reserved, they will not appear as keys in your Dict
, and will cause trouble if used in the wrong way. Example:
>>> a = Dict(__parent=2, __key='a')
>>> a.v = 2
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/Users/mats/dev/mewwts/addict/addict/addict.py", line 28, in __setattr__
self[name] = value
File "/Users/mats/dev/mewwts/addict/addict/addict.py", line 39, in __setitem__
p.__setattr__(key, self)
AttributeError: 'int' object has no attribute 'a'