简体   繁体   English

在defaultdict(列表)中汇总数字

[英]Summing up numbers in a defaultdict(list)

I've been experimenting trying to get this to work and I've exhausted every idea and web search. 我一直在尝试使它生效,并且用尽了所有想法和网络搜索。 Nothing seems to do the trick. 似乎没有办法解决问题。 I need to sum numbers in a defaultdict(list) and i just need the final result but no matter what i do i can only get to the final result by iterating and returning all sums adding up to the final. 我需要对defaultdict(list)数字sum ,而我只需要最终结果,但是无论我做什么,我都只能通过迭代并返回所有总和得出最终结果来得出最终结果。 What I've been trying generally, 我一直在尝试的东西,

d = { key : [1,2,3] }
running_total = 0

#Iterate values
for value in d.itervalues:
  #iterate through list inside value
  for x in value:       
    running_total += x
    print running_total

The result is : 1 , 3 , 6 I understand its doing this because its iterating through the for loop. 其结果是: 136我明白了这样做是因为通过它的迭代for循环。 What i dont get is how else can i get to each of these list values without using a loop? 我没有得到的是在不使用循环的情况下还能如何获得这些列表值中的每一个? Or is there some sort of method iv'e overlooked? 还是有某种方法被人们忽略了?

To be clear i just want the final number returned eg 6 为了清楚起见,我只想返回最终的数字,例如6

EDIT I neglected a huge factor , the items in the list are timedealta objects so i have to use .seconds to make them into integers for adding. 编辑我忽略了一个很大的因素,列表中的项目是timedealta对象,因此我必须使用.seconds使其成为整数以进行添加。 The solutions below make sense and I've tried similar but trying to throw in the .seconds conversion in the sum statement throws an error. 下面的解决方案很有意义,我尝试了类似的方法,但是尝试在sum语句中添加.seconds转换会引发错误。

d = { key : [timedelta_Obj1,timedelta_Obj2,timedelta_Obj3] }

我认为这将为您工作:

sum(td.seconds for sublist in d.itervalues() for td in sublist)

Try this approach: 试试这个方法:

from datetime import timedelta as TD

d = {'foo' : [TD(seconds=1), TD(seconds=2), TD(seconds=3)],
     'bar' : [TD(seconds=4), TD(seconds=5), TD(seconds=6), TD(seconds=7)],
     'baz' : [TD(seconds=8)]}

print sum(sum(td.seconds for td in values) for values in d.itervalues())

You could just sum each of the lists in the dictionary, then take one final sum of the returned list. 您可以对字典中的每个列表sum ,然后对返回的列表sum

>>> d = {'foo' : [1,2,3], 'bar' : [4,5,6,7], 'foobar' : [10]}

# sum each value in the dictionary
>>> [sum(d[i]) for i in d]
[10, 6, 22]

# sum each of the sums in the list
>>> sum([sum(d[i]) for i in d])
38

If you don't want to iterate or to use comprehensions you can use this: 如果您不想迭代或不理解,可以使用以下方法:

d = {'1': [1, 2, 3], '2': [3, 4, 5], '3': [5], '4': [6, 7]}

print(sum(map(sum, d.values())))

If you use Python 2 and your dict has a lot of keys it's better you use imap (from itertools ) and itervalues 如果您使用Python 2并且dict有很多键,那么最好使用imap (来自itertools )和itervalues

from itertools import imap

print sum(imap(sum, d.itervalues())) 

Your question was how to get the value "without using a loop". 您的问题是如何获取“不使用循环”的值。 Well, you can't. 好吧,你不能。 But there is one thing you can do: use the high performance itertools . 但是您可以做一件事:使用高性能itertools

If you use chain you won't have an explicit loop in your code. 如果使用chain ,则代码中不会有显式循环。 chain manages that for you. chain为您管理。

>>> data = {'a': [1, 2, 3], 'b': [10, 20], 'c': [100]}
>>> import itertools
>>> sum(itertools.chain.from_iterable(data.itervalues()))
136

If you have timedelta objects you can use the same recipe. 如果有timedelta对象,则可以使用相同的配方。

>>> data = {'a': [timedelta(minutes=1), 
                  timedelta(minutes=2), 
                  timedelta(minutes=3)], 
            'b': [timedelta(minutes=10), 
                  timedelta(minutes=20)], 
            'c': [timedelta(minutes=100)]}
>>> sum(td.seconds for td in itertools.chain.from_iterable(data.itervalues()))
8160

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM