[Python-Dev] Proposal: defaultdict

Michael Urman murman at gmail.com
Sat Feb 18 06:38:52 CET 2006

On 2/17/06, Adam Olsen <rhamph at gmail.com> wrote:
> if key in d:
>   dosomething(d[key])
> else:
>   dosomethingelse()
> try:
>   dosomething(d[key])
> except KeyError:
>   dosomethingelse()

I agree with the gut feeling that these should still do the same
thing. Could we modify d.get() instead?

>>> class ddict(dict):
...     default_value_factory = None
...     def get(self, k, d=None):
...         v = super(ddict, self).get(k, d)
...         if v is not None or d is not None or
self.default_value_factory is None:
...             return v
...         return self.setdefault(k, self.default_value_factory())
>>> d = ddict()
>>> d.default_value_factory = list
>>> d.get('list', [])
>>> d['list']
Traceback (most recent call last):
  File "<stdin>", line 1, in ?
KeyError: 'list'
>>> d.get('list').append(5)
>>> d['list']

There was never an exception raised by d.get so this wouldn't change
(assuming the C is implemented more carefully than the python above).
What are the problems with this other than, like setdefault, it only
works on values with mutator methods (i.e., no counting dicts)? Is the
lack of counting dicts that d.__getitem__ supports a deal breaker?

>>> d.default_value_factory = int
>>> d.get('count') += 1
SyntaxError: can't assign to function call

How does the above either in dict or a subclass compare to five line
or smaller custom subclasses using something like the following?
    def append(self, k, val):
        self.setdefault(k, []).append(val)
    def accumulate(self, k, val):
        try: self[k] += val
        except KeyError: self[k] = val

Michael Urman  http://www.tortall.net/mu/blog

More information about the Python-Dev mailing list