大循环巢设计,无论如何要提高速度?

时间:2014-03-18 12:22:40

标签: python performance algorithm

我想遍历列表并检查其中的所有可能组合。目前,我正在使用一系列嵌套for循环,显然我对使用此方法的速度并不欣喜若狂。它非常慢,可能需要20-30分钟才能完成所有组合。

for n1 in list1:
    list.append(n1)
    for n2 in list2:
        list.append(n2)
        for n3 in list2:
            list.append(n3)
            for n4 in list3:
                list.append(n4)
                for n5 in list3:
                    list.append(n5)
                    for n6 in list4:
                        list.append(n6)
                        for n7 in list4:
                            list.append(n7)
                            for n8 in list5:
                                list.append(n8)
                                for n9 in list5:
                                    list.append(n9)
                                    some logic that determines a value
                                list.remove(n9)
                            list.remove(n8)
                        list.remove(n7)
                    list.remove(n6)
                list.remove(n5)
            list.remove(n4)
        list.remove(n3)
    list.remove(n2)
list.remove(n1)

我并不幻想这是一个很好的方法。我想不出更好的处理方法。最终是一个TON的组合,但我需要计算每个组合的值。有5个列表,我需要检查的组合包括列表1中的一个,以及列表2-5中的两个点。

如果有人有关于如何改进这个或者在python中的建议来提高速度,那将是值得赞赏的。

最终的组合看起来像这样:

List1[n1], list2[n2], list2[n3], list3[n4], list3[n5], list4[n6], list4[n7], list5[n8], list5[n9]. 

此外,还有一些组合,其中list2例如可以是list2[0],list2[1]list2[1], list2[0],对于我来说,它们是相同的。消除这样的重复可能会减少我的组合,但我不确定如何处理它。

2 个答案:

答案 0 :(得分:4)

看起来您想要涵盖从list1中挑选的一个项目的所有组合,然后是list2 - list5中的两个项目。如果正确,你当然可以提高效率:

from itertools import chain, combinations, product

for comb in product(combinations(list1, 1),
                    combinations(list2, 2),
                    combinations(list3, 2), ...):

每个comb都采用((l1,), (l2, l2), (l3, l3), (l4, l4), (l5, l5))形式,但您可以使用chain.from_iterable将其展平:

comb = list(chain.from_iterable(comb))

获取[l1, l2, l2, l3, l3, l4, l4, l5, l5]

如果不是实际效率,为了提高整洁度,您可以定义要使用的列表以及从每个预先选择的项目数量:

lists = [(list1, 1), (list2, 2), (list3, 2), (list4, 2), (list5, 2)]

for comb in product(*(combinations(l, n) for l, n in lists)):

答案 1 :(得分:0)

我现在正在使用@tobias_k建议的代码

from itertools import product, combinations
player_combinations = product(combinations(C, 1),
                              combinations(PG, 2),
                              combinations(SG, 2),
                              combinations(PF, 2),
                              combinations(SF, 2))
lineuplist = []
for lineups in player_combinations:
    salary = 0
    names = []
    for players in lineups:
        salary += sum(int(player[2]) for player in players)
    if salarycap - undersalary <= salary <= salarycap:
        for players in lineups:
            names += [player[1] for player in players]
        lineuplist.append(names)
        print(str(names) + " $" + str(salary))

现在有人提出改进建议吗?另外,使用itertools重复PG [0],PG [1]和PG [1]的迭代,PG [0]反转组合吗?