Bin-packing(或背包?)问题

时间:2010-10-07 20:20:43

标签: algorithm optimization computer-science

我有一个43到50个数字的集合,范围从0.133到0.005(但主要是小方面)。如果可能的话,我想找到L和R之间总和的所有组合,它们非常接近。*

强力方法采用2 43 至2 50 步骤,这是不可行的。在这里使用什么方法很好?

编辑:组合将用于计算并被丢弃。 (如果您正在编写代码,您可以假设它们只是输出;我会根据需要进行修改。)组合的数量可能太大而无法保存在内存中。

* L = 0.5877866649021190081897311406,R = 0.5918521703507438353981412820。

3 个答案:

答案 0 :(得分:1)

您没有向我们提供足够的信息。但是如果你真的想要输出每个可能的组合,那听起来你有麻烦了。例如,与你告诉我们的一致,每个数字都是〜.027。如果是这种情况,那么每个半数元素的集合都满足您的标准。但是有43个选择21个这样的集合,这意味着你必须输出至少1052049481860集。 (太多不可行)

当然,运行时间不会超过所需输出的长度。

答案 1 :(得分:1)

基本思想是将其转换为整数背包问题(这很容易)。

选择一个小实数e并将原始问题中的数字舍入为k*e的整数ke越小,整数越大(效率权衡),但修改后的问题的解决方案将更接近原始问题。 e=d/(4*43)其中d是目标间隔的宽度应该足够小。

如果修改后的问题有一个精确的解决方案,总结到目标区间的中间(舍入到e),则原始问题在区间内某处有一个。

答案 2 :(得分:0)

实际上,有一个更快的方法:

(蟒)

sums_possible = [(0, [])]
# sums_possible is an array of tuples like this: (number, numbers_that_yield_this_sum_array)
for number in numbers:
    sums_possible_for_this_number = []
    for sum in sums_possible:
        sums_possible_for_this_number.insert((number + sum[0], sum[1] + [number]))
    sums_possible = sums_possible + sums_possible_for_this_number

results = [sum[1] for sum in sums_possible if sum[0]>=L and sum[1]<=R]

另外,Aaron是对的,所以这可能对您不适用