Multiple levels of 'collection.defaultdict' in Python Multiple levels of 'collection.defaultdict' in Python python python

Multiple levels of 'collection.defaultdict' in Python


Use:

from collections import defaultdictd = defaultdict(lambda: defaultdict(int))

This will create a new defaultdict(int) whenever a new key is accessed in d.


Another way to make a pickleable, nested defaultdict is to use a partial object instead of a lambda:

from functools import partial...d = defaultdict(partial(defaultdict, int))

This will work because the defaultdict class is globally accessible at the module level:

"You can't pickle a partial object unless the function [or in this case, class] it wraps is globally accessible ... under its __name__ (within its __module__)" -- Pickling wrapped partial functions


Look at nosklo's answer here for a more general solution.

class AutoVivification(dict):    """Implementation of perl's autovivification feature."""    def __getitem__(self, item):        try:            return dict.__getitem__(self, item)        except KeyError:            value = self[item] = type(self)()            return value

Testing:

a = AutoVivification()a[1][2][3] = 4a[1][3][3] = 5a[1][2]['test'] = 6print a

Output:

{1: {2: {'test': 6, 3: 4}, 3: {3: 5}}}