如何获得n个被10整除且总和为100的数字的组合?

问题描述 投票:0回答:2

[目标是获得分发列表,这些列表允许例如通过对具有不同熟悉权重的变量进行加权来测试场景,这些总和等于100(因此可以与百分比相结合)。

我在下面提出的方法有效,但可能不是最佳方法。随时提出任何改进建议。

python algorithm search combinations subset-sum
2个回答
1
投票

将整数合成为n个部分的函数:

def comppercents(n):
    y = [0] * n
    y[0]  = 100
    while True:
        yield(y)
        v = y[-1]
        if (100 ==v ):
            break
        y[-1] = 0
        j = -2
        while (0==y[j]):
            j -= 1
        y[j] -= 10
        y[j+1] = 10 + v

for x in comppercents(3):
    print(x)


[100, 0, 0]
[90, 10, 0]
[90, 0, 10]
[80, 20, 0]
...
[0, 20, 80]
[0, 10, 90]
[0, 0, 100]

(66个变体)


0
投票
from itertools import groupby

def comb_100(n):
    global L_combination_100 
    L_combination_100= []

    # adds in L_combination_100 all the possible lists (without the order mattering) whose sum of the elements is 10
    find_raw_combination([i+1 for i in list(range(10))]*10,10)

    # we remove all duplicate lists
    for i in range(len(L_combination_100)):
        L_combination_100[i].sort()
    L_combination_100.sort()
    L_combination_100 = list(k for k,_ in groupby(L_combination_100)) # groupby from itertools

    # We remove all lists that have too many elements (> n)
    L_combination_100 = [i if len(i)<=n else [] for i in L_combination_100]
    L_combination_100 = [x for x in L_combination_100 if x != []]

    # We add 0's to lists that don't have n items
    # All items within each list are multiplied by 10 to obtain a sum equal to 100
    for i,l in enumerate(L_combination_100) :
        if len(l) != n:
            L_combination_100[i].extend([0]*(n-len(l)))
        L_combination_100[i] = [ii*10 for ii in L_combination_100[i]]

    #That's how we got our final list of lists/combinations. We have to be careful that the order doesn't matter in these lists.
    return L_combination_100

#Strongly inspired from https://stackoverflow.com/questions/4632322/finding-all-possible-combinations-of-numbers-to-reach-a-given-sum
def find_raw_combination(numbers, target, partial=[]): # need global variable L_combination_100
    s = sum(partial)

    # check if the partial sum is equals to target
    if s == target: 
        L_combination_100.append(partial) if partial not in L_combination_100 else L_combination_100
    if s >= target:
        return # reach if we get the number

    for i in range(len(numbers)):
        n = numbers[i]
        remaining = numbers[i+1:]
        find_raw_combination(remaining, target, partial + [n])

示例:

comb_100(3)

输出:

[[10, 10, 80],
 [10, 20, 70],
 [10, 30, 60],
 [10, 40, 50],
 [10, 90, 0],
 [20, 20, 60],
 [20, 30, 50],
 [20, 40, 40],
 [20, 80, 0],
 [30, 30, 40],
 [30, 70, 0],
 [40, 60, 0],
 [50, 50, 0],
 [100, 0, 0]]
© www.soinside.com 2019 - 2024. All rights reserved.