On Sat, 19 Mar 2005 01:24:57 GMT, "Raymond Hettinger" <[EMAIL PROTECTED]> wrote:
>I would like to get everyone's thoughts on two new dictionary methods: > > def count(self, value, qty=1): > try: > self[key] += qty > except KeyError: > self[key] = qty > > def appendlist(self, key, *values): > try: > self[key].extend(values) > except KeyError: > self[key] = list(values) > >The rationale is to replace the awkward and slow existing idioms for dictionary >based accumulation: > > d[key] = d.get(key, 0) + qty > d.setdefault(key, []).extend(values) > >In simplest form, those two statements would now be coded more readably as: > > d.count(key) > d.appendlist(key, value) > >In their multi-value forms, they would now be coded as: > > d.count(key, qty) > d.appendlist(key, *values) How about an efficient duck-typing value-incrementer to replace both? E.g. functionally like: >>> class xdict(dict): ... def valadd(self, key, incr=1): ... try: self[key] = self[key] + type(self[key])(incr) ... except KeyError: self[key] = incr ... >>> xd = xdict() >>> xd {} >>> xd.valadd('x') >>> xd {'x': 1} >>> xd.valadd('x', range(3)) Traceback (most recent call last): File "<stdin>", line 1, in ? File "<stdin>", line 3, in valadd TypeError: int() argument must be a string or a number >>> xd.valadd('y', range(3)) >>> xd {'y': [0, 1, 2], 'x': 1} >>> xd.valadd('z', (1,2)) >>> xd {'y': [0, 1, 2], 'x': 1, 'z': (1, 2)} >>> xd.valadd('x', 100) >>> xd['x'] 101 >>> xd.valadd('y', range(3,6)) >>> xd['y'] [0, 1, 2, 3, 4, 5] >>> xd.valadd('z', (3,4)) >>> xd['z'] (1, 2, 3, 4) >ISSUES >------ > >The proposed names could possibly be improved (perhaps tally() is more active >and clear than count()). I'm thinking the idea that the counting is happening with the value corresponding to the key should be emphasised more. Hence valadd or such? > >The appendlist() method is not as versatile as setdefault() which can be used >with other object types (perhaps for creating dictionaries of dictionaries). >However, most uses I've seen are with lists. For other uses, plain Python code >suffices in terms of speed, clarity, and avoiding unnecessary instantiation of >empty containers: > > if key not in d: > d.key = {subkey:value} > else: > d[key][subkey] = value > Yes, but duck typing for any obj that supports "+" gets you a lot, ISTM at this stage of this BF ;-) Regards, Bengt Richter -- http://mail.python.org/mailman/listinfo/python-list