将x减到0的最小操作数. - 备战技术面试?力扣提供海量技术面试资源,帮助你高效提升编程技能,轻松拿下世界 IT 名企 Dream Offer。https://leetcode.cn/problems/minimum-operations-to-reduce-x-to-zero/
这个题使用到的是滑动窗口。
乍一看,这个题很奇怪,怎么会是用滑动窗口呢?一个数组操作最左边,操作最右边,并且返回最小的操作数,这该怎么操作?
我们换一个思路,既然操作最左边,操作最右边,我们干脆就操作中间那个部分,反着来。
既然题目要求的是操作a,b两个区域,我们干脆操作中间这个连续的区域。题目给的是x,x是在ab区域里面的数值,那么我们只要用整个数组的和,减去x,不就是中间区域的值的吗?
我们首先先让规定中间区域的目标值 target = sum - x
此时进入滑动窗口,让left和right都从最左边开始。right向右遍历,把right经过的数字累加起来,一直到right大于或者等于target
如果是大于target则用循环来使left向右移动,也就是出窗口
如果是正好等于target则说明这就是一组结果, 记录下此时的结果
等到right一直遍历完整个数组,找到所有符合结果的数据,再取最大的作为结果,别忘了最后的结果是需要用数组的长度减去最大的长度,才是符合题目要求的结果。
代码:
class Solution {
public int minOperations(int[] nums, int x) {
int sum = 0;
for(int a : nums){
sum += a;
}
int target = sum - x;
if(target < 0){
return -1;
}
int ret = -1;
for(int left = 0, right = 0, tmp = 0; right < nums.length; right++){
tmp += nums[right];
while(tmp > target){
tmp -= nums[left++];
}
if(tmp == target){
ret = Math.max(ret , right - left + 1);
}
}
if(ret == -1){
return ret;
}else{
return nums.length - ret;
}
}
}