Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/401.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 如何解决可变性最小最大除法_Javascript_Algorithm_Binary Search Tree - Fatal编程技术网

Javascript 如何解决可变性最小最大除法

Javascript 如何解决可变性最小最大除法,javascript,algorithm,binary-search-tree,Javascript,Algorithm,Binary Search Tree,我一直在努力解决1H30的编码问题,以及如何用二进制搜索解决这个问题。我找到了答案,但我不明白背后的逻辑。有人能告诉我这个答案吗 这就是问题所在 任务描述 给定整数K、M和非空的零索引数组a 由N个整数组成。数组中的每个元素都不是更大的 比M 您应该将此数组划分为K个连续元素块。 块的大小是介于0和N之间的任意整数 数组应该属于某个块 从X到Y的块总和等于A[X]+A[X+1]+…+A[Y]。 空块的和等于0 大和是任何块的最大和 例如,给定整数K=3、M=5和这样的数组 即: A[0]=2A[

我一直在努力解决1H30的编码问题,以及如何用二进制搜索解决这个问题。我找到了答案,但我不明白背后的逻辑。有人能告诉我这个答案吗

这就是问题所在

任务描述

给定整数K、M和非空的零索引数组a 由N个整数组成。数组中的每个元素都不是更大的 比M

您应该将此数组划分为K个连续元素块。 块的大小是介于0和N之间的任意整数 数组应该属于某个块

从X到Y的块总和等于A[X]+A[X+1]+…+A[Y]。 空块的和等于0

大和是任何块的最大和

例如,给定整数K=3、M=5和这样的数组 即:

A[0]=2A[1]=1A[2]=5A[3]=1A[4]=2A[5]=2
A[6]=2

例如,可以将阵列划分为以下块:

[2,1,5,1,2,2,2],[],金额较大的15;[2], [1, 5, 1, 2] ,[2,2]中的一个较大的值为9;[2,1,5],[1,2,2,2]和 大额8元;[2,1]、[5,1]、[2,2,2]以及一个6的大总和

目标是最大限度地减少巨额金额。在上面的示例中,6是 最小的大数目

编写一个函数:

函数解(K,M,A)

给定整数K,M和非空的零索引数组a 由N个整数组成,返回最小的大和

例如,给定K=3,M=5和数组A,使得:

A[0]=2A[1]=1A[2]=5A[3]=1A[4]=2A[5]=2
A[6]=2

函数应该返回6,如上所述

假设:

N和K是[1..100000]范围内的整数; M是[0..10000]范围内的整数; 数组A的每个元素都是[0..M]范围内的整数

这是我能得到的答案

function solution(K, M, A) {
    var begin = A.reduce((a, v) => (a + v), 0)
    begin = parseInt((begin+K-1)/K, 10);
    var maxA = Math.max(A);
    if (maxA > begin) begin = maxA;

    var end = begin + M + 1;
    var res = 0;

    while(begin <= end) {
        var mid = (begin + end) / 2;
        var sum = 0;
        var block = 1;
        for (var ind in A) {
            var a = A[ind];
            sum += a;
            if (sum > mid) {
                ++block;
                if (block > K) break;
                sum = a;
            }
        }
        if (block > K) {
            begin = mid + 1;
        } else {
            res = mid;
            end = mid - 1;
        }
    }
    return res;
}
函数解(K,M,A){
var begin=A.reduce((A,v)=>(A+v),0)
begin=parseInt((begin+K-1)/K,10);
var maxA=数学最大值(A);
如果(maxA>begin)begin=maxA;
var end=begin+M+1;
var-res=0;
while(中期开始){
++块;
如果(块>K)中断;
总和=a;
}
}
如果(块>K){
开始=中间+1;
}否则{
res=中等;
结束=中间-1;
}
}
返回res;
}

这是解决方案中的一个关键问题。对于每个候选解,我们在整个数组上迭代一次,在超过候选解之前,将数组块填充到块可以达到的最大和。如果求和不可行,那么尝试较小的求和是没有意义的,因此我们搜索更高可能的候选空间。如果求和是可以实现的,我们可以尝试较低的候选空间。

这是一个关于解决方案的问题。对于每个候选解,我们在整个数组上迭代一次,在超过候选解之前,将数组块填充到块可以达到的最大和。如果求和不可行,那么尝试较小的求和是没有意义的,因此我们搜索更高可能的候选空间。如果求和是可以实现的,我们可以尝试较低的候选空间。

我对代码做了一点修改,使其更清晰,但下面是我的解释:

/*
K=块数
M=最大数量
A=数组
*/
函数解决方案(numberOfBlocks、maxNumber、array){
让begin=array.reduce((a,b)=>(a+b),0);//计算a的总和
begin=Math.ceil(begin/numberOfBlocks);//计算每个块的平均值
begin=Math.max(begin,Math.max(…数组));//如果>大于平均值,则将begin设置为数组中的最大值
//简而言之:begin现在是可能的最小块和
//计算最大可能的块和
让end=begin+maxNumber+1;
var结果=0;
而(开始)中点意味着我们是
//在另一个街区。。。
如果(currentBlockSum>中点){
++块;
//…所以我们用当前的数字重置总和
currentBlockSum=数字;
//但是如果我们没有区块,我们的猜测(中点)是错误的
//我们必须调整它
如果(块>块数)
打破
}
}
//如果我们没有街区了
//这意味着我们的猜测(中点)比我们想象的要大
如果(块>块数){
开始=中点+1;
//否则,它会更小
}否则{
结果=中点;
结束=中点-1;
}
}
返回结果;

}
我对代码做了一点修改,使其更加清晰,但以下是我的解释:

/*
K=块数
M=最大数量
A=数组
*/
函数解决方案(numberOfBlocks、maxNumber、array){
让begin=array.reduce((a,b)=>(a+b),0);//计算a的总和
begin=Math.ceil(begin/numberOfBlocks);//计算每个块的平均值
begin=Math.max(begin,Math.max(…数组));//如果>大于平均值,则将begin设置为数组中的最大值
//简而言之:begin现在是可能的最小块和
//计算最大可能的块和
让end=begin+maxNumber+1;
var结果=0;
而(开始)中点意味着我们是
//在另一个街区。。。
如果(currentBlockSum>中点){
++块;
//…所以我们用当前的数字重置总和
currentBlockSum=数字;
//但是如果我们没有区块,我们的猜测(中点)是错误的
//我们必须调整它
如果(块>块数)
打破
}
}
//如果我们