|
|
Subscribe / Log in / New account

Python dictionary "addition" and "subtraction"

Python dictionary "addition" and "subtraction"

Posted Mar 15, 2019 23:56 UTC (Fri) by quietbritishjim (subscriber, #114117)
In reply to: Python dictionary "addition" and "subtraction" by jani
Parent article: Python dictionary "addition" and "subtraction"

The values in Counter don't need to be integers, or even numbers. Both the constructor and the update method can take either iterables or mappings, and the iterable versions put integer counts in while the mapping versions just directly use the values (with the + operator, in the case of update). There's a note in the documentation [1] (scroll down to grey box) saying the implementation of each method makes minimal assumptions on the value type.

[1] https://docs.python.org/3/library/collections.html#collec...


to post comments

Python dictionary "addition" and "subtraction"

Posted Mar 17, 2019 11:35 UTC (Sun) by jani (subscriber, #74547) [Link] (1 responses)

Given two dictionaries mapping string keys to list values, how do you actually use Counter to concatenate the lists (list + operation) for keys that exist in both dictionaries?

Python dictionary "addition" and "subtraction"

Posted Mar 20, 2019 20:48 UTC (Wed) by quietbritishjim (subscriber, #114117) [Link]

Hmm, it turns out it doesn't work. The obvious thing is to use +:

Counter({'a': [1], 'b': [1, 2]}) + Counter({'a': [2, 3], 'b': [3]})

This fails for two reasons:

  • The + operator is guaranteed to include only positive results even if summing the values is negative, so it includes the comparison <0 for each element, which fails for lists.
  • If the set of keys is different on the two sides then it does an addition with 0 (this only applies to keys missing in the left hand list, but that is presumably an implementation detail).

An alternative is to use the update() method, which doesn't have a restriction to positive values so doesn't compare against zero:

c = Counter({'a': [1], 'b': [1, 2]})
c.update(Counter({'a': [2, 3], 'b': [3]}))

But this doesn't work either:

  • As with the + operator, missing keys are interpreted as having value 0.
  • The values are passed to + in the opposite order than you would expect, so the above example results in c['a'] == [2,3,1]! This is true in Python 3.7 but not Python 2.7.

I think this is a bug in the documentation, which seems to say that these should be possible (at least for update()), or even a straight up bug in the code. But in fairness it is an unusual use of the class.


Copyright © 2025, Eklektix, Inc.
Comments and public postings are copyrighted by their creators.
Linux is a registered trademark of Linus Torvalds