繁体   English   中英

查找(或生成)等于给定总和的正数的所有可能组合(以给定长度)。(python)

[英]Finding(or Generating) all possible combinations(at a given length) of positive numbers that equals a given sum.(python)

我试图找到最有效的方法来找到等于给定总和的所有数字组合。

例如:寻找总和 = 3 的所有 3 数组合

期望输出:[0,0,3], [0,3,0], [3,0,0], [1,1,1], [1,2,0], [1,2,0] , [2,1,0], [2,0,1]

在应用方面,我试图生成等于 100 的所有 3 编号组合的列表。我尝试通过创建一个包含数字 0 - 100 的列表作为输入参数和以下代码来实现这一点:

 def weightList():
     l=[]
     for x in range(0,101):
         l.append(x)
     return l

    def subset_sum(numbers, target, partial=[]):
        s = sum(partial)

     # check if the partial sum is equals to target
        if (s == target)&(len(partial) == LoanCount): 
            print(partial)
        if s >= target:
            return  # if we reach the number why bother to continue

        for i in range(len(numbers)):
            n = numbers[i]
            remaining = numbers[i+1:]
            subset_sum(remaining, target, partial + [n]) 
  o=weightList()
  subset_sum(o,100)

问题是由于它必须执行的迭代数量太长。 我还需要包含重复元素的组合和不同的元素顺序/序列。 这个方法不行。 谁能为我提供一种更快/更有效的方法来获得我想要的结果?

您可以使用生成器找到等于给定总和的 3 个数字的所有可能组合:

def gen_combo_target(s):
    for i in range(s + 1):
        s2 = s - i
        for j in range(s2 + 1):
            yield (i, j , s - i - j)

list(gen_combo_target(3))

输出:

[(0, 0, 3),
 (0, 1, 2),
 (0, 2, 1),
 (0, 3, 0),
 (1, 0, 2),
 (1, 1, 1),
 (1, 2, 0),
 (2, 0, 1),
 (2, 1, 0),
 (3, 0, 0)]

看看星星和酒吧的问题。 问题是,即使是最快的解决方案仍然会很慢,因为答案的数量非常多(可能是 N 的数量级!),并且任何正确的解决方案都需要得到所有答案。

这是我对解决方案的看法:

def get_combinations(n, k): # gets all lists of size k summing to n
    ans = []
    def solve(rem, depth, k, cur):
        if depth == k:
            ans.append(cur)
        elif depth == k-1:
            solve(0, depth+1, k, cur + [rem])
        else:
            for i in range(rem+1):
                solve(rem-i, depth+1, k, cur+[i])
    solve(n, 0, k, [])
    return ans

print (get_combinations(3,3))

尽可能快地找到所有可能的列表。 但是,如果您只想找到此类列表的数量,则可以使用上面引用的星形和条形方法更快地完成。

您还可以像这样使用生成器和 python itertools:

from itertools import product

def comb(nx):
    list_gen = (n for n in range(nx+1))
    list_ = (list(list_gen))
    prod = [seq for seq in product(list_, list_, list_) if sum(seq) == nx]    
    print(list(prod))

结果:

[(0, 0, 3), (0, 1, 2), (0, 2, 1), (0, 3, 0), (1, 0, 2), (1, 1, 1), (1, 2, 0), (2, 0, 1), (2, 1, 0), (3, 0, 0)]

它可以在我的机器上运行大约 10 us:

9.53 µs ± 177 ns per loop (mean ± std. dev. of 7 runs, 100000 loops each)

暂无
暂无

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

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