算法:元素个数为2n的数组,把数组分割为元素个数为n的两个数组,并使这两个子数组的和最接近

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了算法:元素个数为2n的数组,把数组分割为元素个数为n的两个数组,并使这两个子数组的和最接近相关的知识,希望对你有一定的参考价值。

例如有如下数组有10个元素,将其分成两个数组,每个数组有5个元素,且每个数组中的元素和最接近相等

1、5、7、8、9、6、3、11、20、17

1、3、11、8、20 5、7、9、6、17

书上说道:假设2n个整数之和为SUM。从2n个整数中找出n个元素的和,有三种可能:大于SUM/2,等于SUM/2和小于SUM/2。而这两种情况没有本质的区别。

为什么书上说“等于SUM/2和小于SUM/2”没有本质区别呢?
为什么不说”大于SUM/2和等于SUM/2“没有本质区别?
费解

先按大小排序,然后截取前四分之一和最后四分之一凑成新的数组。(代码手写的,没验证过,可能会有错误。另外排序完全可以使用Arrays.sort()来完成)

class MyProgram

//对数组进行排序,从小到大
public int[] mySory(int[] arr)
int temp;
for(int j = arr.length();j>0;j--)
for(int i = 1;i<arr.length();i++)
if(arr[i]>arr[i+1])
temp = arr[i+1];
arr[i+1]=arr[i];
arr[i]=temp;



return arr;
 
/从数组中选择头尾,并分成两个和相近的数组
public int[] myArr(int arr)
int length = arr.length()/2;
int[] arrA = new int[length];

for(int i = 0;i<length/2;i++)
arrA[i] = arr[i];

for(int i = 0;i<length/2;i++)
arra[length/2+i+1]=arr[length-i];

return arrA;

参考技术A 因为对于这个问题来说,我们只需要找出集合S(2N, N)中与SUM/2最接近的那个和。令S(k, i)表示前k个元素中任意i个元素的和的集合。
我们在这个过程中只需要关注和不大于SUM/2的那个子数组的和。所以集合中重复的和以及大于SUM/2的和都是没有意义的。追问

那把"大于SUM/2和等于SUM/2"看成一组也行吧?因为只要个大致范围是吧?

追答

对的,是这样。把谁看成一组影响到后面的算法。如果选的是等于和小于,只需要从SUM/2到1遍历一次,逐个询问这个值是不是在S(2N,N)中出现。反之需要从SUM/2到SUM遍历一次,逐个询问这个值是不是在S(2N,N)中出现。

参考技术B 有,区别可打了!

以上是关于算法:元素个数为2n的数组,把数组分割为元素个数为n的两个数组,并使这两个子数组的和最接近的主要内容,如果未能解决你的问题,请参考以下文章

编程之美数组分割

求算法,将N个整数分到M个数组中,要求元素和相差最小,元素个数相差最小

二维数组元素个数的算法

luogu 5426

PriorityQueue源码解析

选择排序——2堆排序实现