Leetcode:209.长度最小的子数组

413 阅读1分钟

力扣题目链接

题目描述:

给定一个含有 n 个正整数的数组和一个正整数 s ,找出该数组中满足其和 ≥ s 的长度最小的 连续 子数组,并返回其长度。如果不存在符合条件的子数组,返回 0。

示例:

输入:s = 7, nums = [2,3,1,2,4,3] 输出:2 解释:子数组 [4,3] 是该条件下的长度最小的子数组。

方法一:暴力解法

思路:

  • for循环遍历数组nums,并用sum对数组元素进行累加
  • 应该嵌套一层for循环,来保存这个子数组。j是指向子串的末尾,即已找到子数组
  • 当sum>=s时,则说明找到了这个子数组
var minSubArrayLen = function(target, nums) {
    //sum计算子串的和,subLengt为子数组的长度
    let sum = 0, subLength =0
    let result = Infinity
    for (let i=0;i<nums.length;i++){
        //i每指向一个新的数,sum要归0
        sum = 0
        for(let j = i;j<nums.length;j++){
        //j为子串结束的指向
            sum += nums[j]
            if(sum >= target){
                subLength = j-i+1//子串的长度
                result = result<subLength?result:subLength
                break
            }
        }
    }
    return result==Infinity?0:result

};

方法二:滑动窗口

思路:

  • 滑动窗口可以看成是一个连续的子数组,但是它的特别之处在于它可以收缩
  • 滑动窗口收缩即希望我们的目标连续子数组的长度最短:因为子数组头部的数可能比较小,而子数组尾部的数比较大,所以当我们首次找到符合条件的连续子数组时,通过缩小窗口的大小(通过i也就是调节滑动窗口的起始位置),可以找到长度最小的连续子数组

209.长度最小的子数组.gif

var minSubArrayLen = function(target, nums) {
   let subLength = 0,sum=0,result=Infinity
   let i = 0//滑动窗口的起始位置
   for(let j = 0;j<nums.length;j++){
       //j为滑动窗口的结束位置
       sum += nums[j]
       while(sum>target){
           subLength=(j-i+1)
           result = result<subLength?result:subLength
           sum -= nums[i++]
       }
   }
    return result == Infinity?0:result

};