将数组拆分为权重相似的子数组

时间:2018-10-24 01:54:40

标签: algorithm optimization load-balancing mathematical-optimization

我有一个n个正数数组。我需要将其拆分为N个连续的子数组; n > N

我需要最小化[max S(j) over j] - [min S(j) over j], 其中S(j)表示j-th子数组(j = 1,...,N)中元素的总和。

即,所有子数组的元素总数应“相同”。

我确定这个问题是已知的。有人可以指出我算法,实现或出版物吗?

2 个答案:

答案 0 :(得分:1)

此问题等效于找到max S(j) over all j的最小值。

直觉:

  • 假定所有可能的max S(j) over all j中的最小值为xmax,因此结果将为xmax - xmin

  • 假设另一个ymax > xmax可以为我们提供更好的结果,这意味着ymax - ymin <xmax - xmin-> ymin > xmin-> min S(j) - ymax > min S(j) - xmax,这应该不会发生。

因此,问题指向找到max S(j) over all j的最小值

这可以通过使用二进制搜索来解决。 假设整个数组的总和为X,那么我们有算法:

int start = 0;
int end = X;
int result = 0;
while(start <= end){
    int mid = (start + end)/2;
    for(int i = 0; i < n; i++){
       if sum of current segment > mid
           split

    }
    if total segment > N
       start = mid + 1;
    else 
       update result;
       end = mid - 1;
}

答案 1 :(得分:0)

找到整个数组的总和并调用T,然后执行k = T / N以确定第一个子数组元素的理想总和。然后线性创建第一个子数组(从数组的开头开始),同时在确定子数组是否应该/不应该包含下一个子数组时,尝试最小化ksum of all values in the sub-array so far + potential next element之间的差异元素。

然后使用递归将数组的其余部分拆分为N-1个片段,并在N == 1(数组的其余部分是最后一个子数组)时停止。

注:并非在所有情况下都提供最佳解决方案,但是它相对较快,并且出于(动态)负载平衡的目的,存在这样的风险,即负载会经常变化,以至于任何更昂贵的(总是找到最优解)是没有意义的。