栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 面试经验 > 面试问答

将列表分为两部分,它们的和彼此最接近

面试问答 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

将列表分为两部分,它们的和彼此最接近

问题是NPC,但是有一个伪多项式算法,这是一个2分区问题,您可以按照伪多项式时间算法的方法解决子集总和问题。如果输入大小与输入值在多项式上相关,则可以在多项式时间内完成。

在您的情况下(权重<250)是多项式(因为权重<= 250 n =>和<= 250 n ^ 2)。

令Sum =权重之和,我们必须创建二维数组A,然后逐列构造A

如果(j == weight [i]或j-weight [i] = weight [k](k在列表中)),则A [i,j] = true。

使用此算法创建数组需要O(n ^ 2 * sum / 2)。

最后,我们应该找到具有真正价值的最有价值的专栏。

这是一个例子:

项目:{0,1,2,3}权重:{4,7,2,8} => sum = 21 sum / 2 = 10

items/weights 0|  1  | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10      ---------------------------------------------------------   |0  |  0  | 0 | 0 | 1 | 0 | 1 | 0 | 0 | 0 | 0  |1  |  0  | 0 | 0 | 0 | 0 | 0 | 1 | 0 | 1 | 0  |2  |  0  | 1 | 0 | 0 | 0 | 1 | 0 | 0 | 1 | 1  |3  |  0  | 0 | 0 | 0 | 0 | 0 | 0 | 1 | 0 | 1

因此,因为a [10,2] == true,则分区为10,11

这是我在这里找到的算法,并进行了一些编辑以解决您的问题:

bool partition( vector< int > C ) { // compute the total sum int n = C.size(); int N = 0; for( int i = 0; i < n; i++ ) N += C[i]; // initialize the table  T[0] = true; for( int i = 1; i <= N; i++ ) T[i] = false; // process the numbers one by one for( int i = 0; i < n; i++ )  for( int j = N - C[i]; j >= 0; j--)   if( T[j] ) T[j + C[i]] = true; for(int i = N/2;i>=0;i--)    if (T[i])      return i; return 0;}

我只是返回了第一个T [i],而不是返回T [N / 2](以最大到最小的顺序),这是正确的。

寻找给出该值的路径并不难。



转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/617019.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号