hrk23
hrk23

Reputation: 23

Sum the first value of each tuple in a list

x = [(5,3), (8, 3), (7, 3), (5, 4), (2, 4), (3, 4)]
d = {}
[d.__setitem__(d.get(key1,0)+key1,key2) for key1,key2 in x]
print(list(d.items()))

I want to add the first value in the tuple having the same second value. I have written the code, but i am not able to find my mistake. Any ideas ??

Upvotes: 0

Views: 164

Answers (2)

miradulo
miradulo

Reputation: 29690

Kasramvd already has you covered as for why your approach doesn't work. You could use itertools.groupby to group by second tuple elements, then sum the first elements with operator.itemgetter.

{k: sum(map(itemgetter(0), g)) for k, g in groupby(x, itemgetter(1))}

Evidently if your list wasn't sorted by second tuple elements as it currently is, you would have to sort first.

Demo

>>> from operator import itemgetter
>>> from itertools import groupby
>>> x = [(5,3), (8, 3), (7, 3), (5, 4), (2, 4), (3, 4)]
>>> {k: sum(map(itemgetter(0), g)) for k, g in groupby(x, itemgetter(1))}
{3: 20, 4: 10}

Upvotes: 0

Kasravnd
Kasravnd

Reputation: 107287

__setitem__ returns None, also your logic is wrong too. You need to categorize your items based on the second value then sum their first value up.

You can use collections.defaultdict() for categorization:

In [13]: x = [(5,3), (8, 3), (7, 3), (5, 4), (2, 4), (3, 4)]

In [16]: from collections import defaultdict

In [17]: d = defaultdict(int)

In [18]: for i, j in x:
   ....:     d[j] += i
   ....:     

In [19]: d
Out[19]: defaultdict(<class 'int'>, {3: 20, 4: 10})

You could also use itertools.groupby() within a dictionary comprehension:

In [28]: from itertools import groupby

In [29]: from operator import itemgetter

In [30]: {k: sum(i for i, _ in g) for k, g in groupby(x, itemgetter(1))}
Out[30]: {3: 20, 4: 10}

Note that if your list is not sorted based on second item you need to sort it based on that second item before passing to groupby() function. (In that case this solution would be so inefficient against the defaultdict one)

Upvotes: 2

Related Questions