给定一个非负整数数组和一个整数 m,你需要将这个数组分成 m 个非空的连续子数组。设计一个算法使得这 m 个子数组各自和的最大值最小。
注意: 数组长度 n 满足以下条件:
1 ≤ n ≤ 1000 1 ≤ m ≤ min(50, n) 示例:
输入: nums = [7,2,5,10,8] m = 2
输出: 18
解释: 一共有四种方法将nums分割为2个子数组。 其中最好的方式是将其分为[7,2,5] 和 [10,8],
因为此时这两个子数组各自的和的最大值为18,在所有情况中最小。
解题思路:
使用二分法
先猜出一个mid作为答案,然后以mid为标准取划分数组。
同时记录所需数组的数量need。
如果我们分的数组个数比题目要求的多,那么就意味着我们猜的答案偏小。
然后搜寻右半边。
反之同理。
int splitArray(vector<int>& nums, int m) {
long long lval=0,rval=0;
for(int num:nums){
lval = max(lval,(long long)num);
rval += (long long)num;
}
while(lval<rval){
long long mid=(lval+rval)>>1,cur=0;
int need=1;
for(int num:nums){
if(cur+num>mid){
++need;
cur=0;
}
cur+=num;
}
if(need>m)
lval=mid+1;
else
rval=mid;
}
return lval;
}