长度最小的子数组(Java详解)

这篇具有很好参考价值的文章主要介绍了长度最小的子数组(Java详解)。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

目录

题目描述

题解

思路分析

暴力枚举代码

滑动窗口代码


题目描述

给定一个含有 n 个正整数的数组和一个正整数 target 。

找出该数组中满足其和 ≥ target 的长度最小的 连续子数组 [numsl, numsl+1, ..., numsr-1, numsr] ,并返回其长度如果不存在符合条件的子数组,返回 0 。

示例:

输入:target = 7, nums = [2,3,1,2,4,3]
输出:2
输入:target = 4, nums = [1,4,4]
输出:1

题解

思路分析

题目要求我们找到和 >= target 最小连续 的子数组,我们很容易想到暴力枚举的方法,即访问数组的每一个元素i,并将i作为第一个元素,向后寻找

长度最小的子数组(Java详解),Java刷题,算法,数据结构,双指针,滑动窗口

暴力枚举代码

class Solution {
    public int minSubArrayLen(int target, int[] nums) {
        int count = 0;
        for(int i = 0; i < nums.length; i++){
            int sum = 0;
            //向后遍历找到以nums[i]为起始元素的最小数组
            for(int j = i; j < nums.length;j++){
                sum += nums[j];
                if(sum >= target){
                     //更新目标值 由于count的初始值为0,因此需要更新初始值,
                     //否则最小值恒为0
                    if(count > j-i+1 || count == 0){
                        count = j-i+1;
                    }
                    break;
                }
            }
        }
        //若count未被更新,则返回0,即没有子数组的和大于target,
        //若count被跟新,则返回最小的子数组长度
        return count;
    }
}

 

此时我们通过遍历访问了数组的每个元素,在访问每个元素时,以该元素为起始元素,并向后寻找其最小长度的子数组,因此时间复制度为O()

而,题目所给的数组中所有元素均是正整数,因此每加上一个元素,子数组的和 sum 增加,通过这个特性,我们可以想到使用滑动窗口来解决这个问题

什么是滑动窗口?

滑动窗口是一种基于双指针的思想,两个指针指向的元素之间形成了一个窗口

因此滑动窗口是通过两个指针来维护的,那么如何移动这两个指针,是使用滑动窗口解决问题的关键

长度最小的子数组(Java详解),Java刷题,算法,数据结构,双指针,滑动窗口

 初始时,两个指针都指向0下标位置

长度最小的子数组(Java详解),Java刷题,算法,数据结构,双指针,滑动窗口

遍历元素,若条件不满足,则将right指针向右移动,直到条件满足为止

长度最小的子数组(Java详解),Java刷题,算法,数据结构,双指针,滑动窗口

条件满足时,则保持右指针不变,开始移动左指针 left

长度最小的子数组(Java详解),Java刷题,算法,数据结构,双指针,滑动窗口

在向窗口中添加新元素或从窗口中删除旧元素时,可能会更新一些与窗口范围有关的数据(例如,本题就需要更新最小子数组的长度)

如何使用滑动窗口解决本题? 

(1)我们定义两个指针left right,并让其都指向数组首元素

 长度最小的子数组(Java详解),Java刷题,算法,数据结构,双指针,滑动窗口

(2)此时窗口内只有 2 这一个元素,不满足和 sum >= target,因此将right向右移动,将新的元素加入窗口中,并判断此时子数组的和 sum 是否大于等于target,若满足,则不再移动right

长度最小的子数组(Java详解),Java刷题,算法,数据结构,双指针,滑动窗口

(3)在sum >= target时,首先判断最小的子数组长度是否需要更新,并保持right不变,向右移动左指针left,删除旧的元素,直到sum < target

长度最小的子数组(Java详解),Java刷题,算法,数据结构,双指针,滑动窗口

(4)循环(2)(3),直到right遍历完数组

为什么可以使用滑动窗口解决本题?
 

因为我们要找的子数组是连续的,且数组中的元素都为正整数,即子数组中增加一个元素,子数组中的元素和sum增加,从窗口中删除一个元素,sum减小,因此我们可以通过改变子数组的两端元素来更新数组,因此可以使用滑动窗口来解决本题

由于左右指针都只遍历了一遍数组,因此时间复杂度O(N)

滑动窗口代码

class Solution {
    public int minSubArrayLen(int target, int[] nums) {
        int left = 0;
        int right = 0;
        int sum = nums[0];
        int len = nums.length;
        int count = 0;
        while(left <= right && right < len){
            //小于目标值,向右移动右指针right
            while(left <= right && right < len && sum < target){
                right++;
                if(right == len){
                    break;
                }
                sum += nums[right];
            }
            //大于等于目标值
            while(left <= right && sum >= target){
                //更新目标值 由于count的初始值为0,因此需要更新初始值,否则最小值恒为0
                if((right - left) < count || count == 0){
                    count = right - left + 1;
                }
                //左边值出窗口,left向右移动
                sum -= nums[left];
                left++;
            }
        }
        //若count未被更新,则返回0,即没有子数组的和大于target,
        //若count被跟新,则返回最小的子数组长度
        return count;
    }
}

题目来自:

LCR 008. 长度最小的子数组 - 力扣(LeetCode)文章来源地址https://www.toymoban.com/news/detail-754091.html

到了这里,关于长度最小的子数组(Java详解)的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 【Leetcode刷题-Python/C++】长度最小的子数组(滑动窗口)

    209.长度最小的子数组 给定一个含有 n 个正整数的数组和一个正整数 target 。 找出该数组中满足其和 ≥ target 的长度最小的 连续子数组 [numsl, numsl+1, …, numsr-1, numsr] ,并返回其长度。如果不存在符合条件的子数组,返回 0 。 输入:target = 7, nums = [2,3,1,2,4,3] 输出:2 解释:子数

    2023年04月08日
    浏览(41)
  • leetcode分类刷题:易混题辨析一、209. 长度最小的子数组 vs 560. 和为K的子数组

    1、刷题慢慢积累起来以后,遇到相似的题目时,会出现算法思路混淆了 2、这两道题都是对 连续子数组加和 进行考察,细节区别在于数组元素在209. 长度最小的子数组为 正整数(窗口增加元素递增,减少元素递减) ,在560. 和为K的子数组为 整数 3、209. 长度最小的子数组采

    2024年02月10日
    浏览(39)
  • [自我记录]随想录刷题第二天 | 977.有序数组的平方,209.长度最小的子数组,59.螺旋矩阵II

     代码随想录打卡第二天, 新手自我记录一下刷题历程, 仅为自我打卡使用. 今天刷了三道主题, 第一道双指针和第三道模拟做出来了, 第二道写出了暴力解法但是提交leetcode超时了, 测试用例过了18/20, 看了carl哥答案以后自己重新补写了滑动窗口方法. 977. 有序数组的平方 简单题

    2024年02月05日
    浏览(45)
  • 【算法专题突破】滑动窗口 - 长度最小的子数组(9)

    目录 1. 题目解析 2. 算法原理 3. 代码编写 写在最后: 题目链接:209. 长度最小的子数组 - 力扣(Leetcode)  要注意的是,题目给的是正整数, 而题目要求并不难理解,就是找最短的子数组。 如果使用暴力的话,就是一个O(N3)的算法,复杂度很高, 我们可以用滑动窗口来做,

    2024年02月09日
    浏览(32)
  • 算法-有序数组的平方,长度最小的子数组,螺旋矩阵II

    伪装成一个老手! 题目 给你一个按 非递减顺序 排序的整数数组 nums,返回每个数字的平方组成的新数组,要求也按非递减顺序排序。 示例 : 输入:nums = [-4,-1,0,3,10] 输出:[0,1,9,16,100] 解释:平方后,数组变为 [16,1,0,9,100] 排序后,数组变为 [0,1,9,16,100] 来源:力扣977 思路 遍

    2024年02月11日
    浏览(42)
  • 算法练习-长度最小的子数组(思路+流程图+代码)

            难度:简单         分类:数组         难度与分类由我所参与的培训课程提供,但需要注意的是,难度与分类仅供参考。以下内容均为个人笔记,旨在督促自己认真学习。         给定一个含有个正整数的数组和一个正整数s,找出该数组中满足其和

    2024年01月18日
    浏览(45)
  • 【算法|滑动窗口No.1】leetcode209. 长度最小的子数组

    个人主页:兜里有颗棉花糖 欢迎 点赞👍 收藏✨ 留言✉ 加关注💓本文由 兜里有颗棉花糖 原创 收录于专栏【手撕算法系列专栏】【LeetCode】 🍔本专栏旨在提高自己算法能力的同时,记录一下自己的学习过程,希望对大家有所帮助 🍓希望我们一起努力、成长,共同进步。

    2024年02月08日
    浏览(42)
  • 算法训练 Day 2 | 数组:977.有序数组的平方,209.长度最小的子数组,59.螺旋矩阵II

    977. 有序数组的平方 第一想法:暴力破解 看完题解想法:朝着双指针方向想 遇到困难: 用双指针的话,一开始想到两边指针往中间靠,逐个将最大值赋给结果数组。和题解不同的是,循环条件我写了  while (left != right) {...} ,相比于题解的  while (left = right) {...} ,我需要在后

    2023年04月12日
    浏览(47)
  • 【LeetCode题目详解】 977.有序数组的平方 209.长度最小的子数组59.螺旋矩阵II day2

    看完这个题目第一想法就是直接暴力解决,直接将全部平方然后进行排序。比如快排。 代码如下: 时间复杂度是 O(nlogn)或者说【O(n + nlogn)】,括号里面这个是为了比较接下来的方法。 然后看了代码随想录的视频学习了用双指针来写这道题的方法(说实话不看视频真没想到可

    2024年02月13日
    浏览(43)
  • 4、长度最小的子数组

            找到一个数组中,有多少个连续元素的和小于某个值,求出连续元素的长度的最小值。         其本质也是快慢指针,一个指针指向窗口的起始位置,另一个指针指向窗口的终止位置。     1.定义快慢指针: 2.更新慢指针: 并记录长度 3. 更新快指针: 4.重复第二步

    2024年02月14日
    浏览(30)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包