如何在向量中找到所有可能的数字和数字差异?

时间:2016-01-17 15:06:20

标签: algorithm subset-sum

我们说我有一个名为数字的向量。 数字= {1,5,6,8}。 (我有一种可能性是将矢量的大小加倍并包括所有负数,但我仍然没有很好的解决方案来找到所有可能的总和。)

可能的解决方案:

4 = 5 - 1

1 = 1

19 = 8 + 6 + 5

我想在我找到一个我要找的号码时停止搜索,但我的主要问题是找到所有不同的总和。

这与子集和问题非常相似,但我还没有真正找到一个我能理解的解决方案/包含负数。

2 个答案:

答案 0 :(得分:0)

使用动态编程。

(a_0, ..., a_{n-1})成为您的数字数组。 设A(k)(a_0, ..., a_{k-1})的所有可能总和/差异的集合。 然后,您可以轻松地从A(k)推断A(k-1)。确保使用哈希表或排序或其他任何内容删除所有重复。

关键是,如果m的上限为a_i,则A(k)最多包含2mk + 1个元素。因此,复杂性从O(3^n)减少到O(mn^2)

这可能是您可以做的最好的事情:例如,如果a_i以指数方式增加,那么最终结果的大小也是指数级的。

答案 1 :(得分:0)

在三元表示{0,1,2}中思考,你有一组数字,其中每个数字都可以显示为正数,负数或不显示,那么你可以将这个可能性表示为三元{0,1,2}并使用它与coef - > {-1,0,1}您可以轻松计算所有组合。 coef - > (-1,0,1) - >三元' 0' - >价值' -1',三元' 1' - >价值' 0'和三元2 - >价值' 1'。

Numbers -> {n0, n1, n2, .. ni}

三元表示 - > (t0)*3^0 + (t1)*3^1 + (t2)*3^2 + .. + (ti)*3^i

Coef - > {c0 , c1, c2, .. ci}

结果 - > C0*n0 + C1*n1 + C2*n2 + .. + Ci*ni

一个例子:

Numbers = {1, 5, 6, 8}

总组合 - > 3^4 = 81

组合数(c)∈[0,80]。

f.e:c = 79 - > 2221(ternary)

三元(反向){1, 2, 2, 2}到coef {0, 1, 1, 1}

结果(79d / 2221t):0*1 + 1*5 + 1*6 + 1*8 = 19

要计算所有组合,您必须在循环(i -> 0 .. 3^4)

中计算此步骤