简体   繁体   English

Python使用组合来对字典中列表中的元组中的值求和?

[英]Python using combinations to sum values in a tuple in a list in a dictionary?

I am trying to sum a combination of values from a list of tuples in a dictionary. 我试图从字典中的元组列表中总结值的组合。 For example, my dictionary contains: 例如,我的字典包含:

dict = {1: [(2, 2), (4, 3), (6, 1), (7, 1), (8, 3)], 2: [(4, 1), (5, 3), (1, 2)],...} 

and goes on for multiple entries. 并继续多次参赛。 I'm trying to sum the second value of the tuples for each entry in as many combinations that sum to a maximum of 4. So for entry 1, the desired output would be: 我试图在最多为4的组合中为每个条目的元组的第二个值求和。因此对于条目1,所需的输出将是:

{1: [(2, 6, 3), (2, 7, 3), (4, 6, 4), (4, 7, 4), (6, 7, 2), (8, 6, 4), (8, 7, 4)]

Where the third value in this tuple is the sum of the combinations of the second value of the previous tuples, and the first and second values of this tuple are the associated first values of the previous tuples. 其中该元组中的第三个值是前一元组的第二个值的组合之和,并且该元组的第一个和第二个值是前一个元组的相关第一个值。

I have tried the following code: 我试过以下代码:

for key, value in dict.items():
    object1 = key
    mylist = value
    for tup in mylist:
         object2 = tup[0]
         pair = tup[1]
         combo = itertools.combinations(tup[1],2)
         sum = {k:sum(j for _,j in v) for k,v in combo}
         if sum <= 4:
             print(sum)

And I get the error 我得到了错误

'numpy.float64' object is not iterable

I think my error stems from "combo" and possibly my use of itertools. 我认为我的错误源于“组合”,可能还有我对itertools的使用。 I am unsure if I just need to fix this section of my code or if I am way off base in my approach. 我不确定我是否只需要修复我的代码的这一部分,或者我是否偏离了我的方法。

Yes, you can do this with itertools.combinations , but you have to pass it the right arguments. 是的,您可以使用itertools.combinations执行此操作,但您必须将正确的参数传递给它。 :) You need to pass it the list of tuples so it can make the pairs of tuples. :)您需要将元组列表传递给它,以便它可以生成元组对。 You could do this with comprehensions, but I think using traditional for loops makes it easier to read. 可以用理解做到这一点,但我认为使用传统的for循环可以更容易阅读。

As others have mentioned, there are other problems with your code, apart from not passing the right things to combinations . 正如其他人所提到的,除了没有将正确的东西传递给combinations之外,您的代码还存在其他问题。 The main one being that you're assigning a dictionary to the name sum , which shadows the sum built-in function that you're also trying to use. 主要的一个是你将字典分配给名称sum ,它会影响你也试图使用的sum内置函数。 And you also attempt to compare that dictionary with the integer 4, that doesn't make a lot of sense. 并且您还尝试将该字典与整数4进行比较,这没有多大意义。 :) :)

Anyway, here's some code that does what you want. 无论如何,这里有一些代码可以满足您的需求。 Note that in your expected output you messed up the last two tuples: (8, 6, 4) and (8, 7, 4) should be (6, 8, 4) and (7, 8, 4) , respectively. 请注意,在您的预期输出中,您搞砸了最后两个元组: (8, 6, 4) 8,6,4 (8, 6, 4)(8, 7, 4)应分别为(6, 8, 4)(7, 8, 4)

from itertools import combinations

a = {
    1: [(2, 2), (4, 3), (6, 1), (7, 1), (8, 3)], 
    2: [(4, 1), (5, 3), (1, 2)],
}

new_dict = {}

for k, seq in a.items():
    c = []
    for (u,v), (x,y) in combinations(seq, 2):
        total = v + y
        if total <= 4:
            c.append((u, x, total))
    new_dict[k] = c

for k, seq in new_dict.items():
    print(k, seq)

output 产量

1 [(2, 6, 3), (2, 7, 3), (4, 6, 4), (4, 7, 4), (6, 7, 2), (6, 8, 4), (7, 8, 4)]
2 [(4, 5, 4), (4, 1, 3)]

combinations(seq, 2) yields pairs of tuples, and we can unpack those tuples into their individual numbers with combinations(seq, 2)产生元组对,我们可以将这些元组解压缩到它们各自的数字中

for (u,v), (x,y) in combinations(seq, 2):

We could have done something like 我们本可以做类似的事情

for t0, t1 in combinations(seq, 2):

and then unpacked the t0 and t1 tuples in a separate step, or just used indexing to get their items. 然后在单独的步骤中解压缩t0t1元组,或者只是使用索引来获取它们的项目。 Eg, 例如,

for t0, t1 in combinations(seq, 2):
    total = t0[1] + t1[1]
    if total <= 4:
        c.append((t[0], t[1], total))

But I think the previous way is less cluttered. 但我认为以前的方式不那么杂乱。


But if you insist on doing it all with comprehensions, you can: 但如果你坚持用理解来做这一切,你可以:

new_dict = {k: [(u, x, v+y) for (u,v), (x,y) in combinations(seq, 2) if v+y <= 4]
    for k, seq in a.items()}

Note that this is less efficient than the previous versions because it computes v+y twice for every combination that passes the v+y <= 4 test. 注意,这是比以前的版本效率较低,因为它计算v+y两次为经过每个组合v+y <= 4测试。

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

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