算法修炼之路之滑动窗口

目录

一:滑动窗口的认识及模板

二:LeetcodeOJ练习

1.第一题

2.第二题

3.第三题

4.第四题

5.第五题

6.第六题

7.第七题

一:滑动窗口的认识及模板

这里先通过一道题来引出滑动窗口

LeetCode 209 长度最小的子数组

画图分析:

具体代码:

cpp 复制代码
int minSubArrayLen(int target, vector<int>& nums) {
        int sum=0,ret=INT_MAX;
        int left=0,right=0;
        while(right<nums.size())
        {
            sum+=nums[right++];//进窗口
            while(sum>=target)//判断
            {
                ret=min(ret,right-left);//更新结果
                sum-=nums[left++];//出窗口
            }
        }

       return  ret==INT_MAX? 0:ret;
    }

二:LeetcodeOJ练习

1.第一题

LeetCode_3 无重复字符的最长子串

画图分析:

具体代码:

cpp 复制代码
int lengthOfLongestSubstring(string s) {
        int hash[129]={0};

        int ret=0;
        for(int left=0,right=0;right<s.size();++right)
        {
            hash[s[right]]++;//进窗口
            while(hash[s[right]]>1)//判断
            {
                hash[s[left++]]--;//出窗口
            }

            ret=max(ret,right-left+1);//更新结果
        }
        return ret;
    }

2.第二题

LeetCode_1004 最大连续1的个数III

画图分析:

具体代码:

cpp 复制代码
int longestOnes(vector<int>& nums, int k) {
        int zero=0,ret=0;
        for(int left=0,right=0;right<nums.size();++right)
        {
            if(nums[right]==0) zero++;//进窗口
            while(zero>k)//判断
            {
                if(nums[left++]==0) zero--;//出窗口
            }
            ret=max(ret,right-left+1);//更新结果
        }

        return ret;
    }

3.第三题

LeetCode-1658 将x减到0的最小操作数

画图分析:

具体代码:

cpp 复制代码
int minOperations(vector<int>& nums, int x) {
        int sum=0;//计算数组和
        for(int e:nums) sum+=e;
        int target=sum-x;
        if(target<0) return -1;

        int ret=-1;
        for(int left=0,right=0,tmp=0;right<nums.size();++right)
        {
            tmp+=nums[right];//进窗口
            while(tmp>target)//判断
            {
                tmp-=nums[left++];//出窗口
            }
            if(tmp==target) ret=max(ret,right-left+1);//更新结果
        }

        if(ret==-1) return -1;
        else return nums.size()-ret;
    }

4.第四题

LeetCode_904 水果成篮

画图分析:

具体代码:

cpp 复制代码
int totalFruit(vector<int>& f) {
       unordered_map<int,int> hash;//统计窗口中水果的种类数
       int ret=0;

       for(int left=0,right=0;right<f.size();++right)
       {
        hash[f[right]]++;//进窗口
        while(hash.size()>2)//判断
        {
            //出窗口
            hash[f[left]]--;
            if(hash[f[left]]==0) hash.erase(f[left]);
            ++left;
        }
        ret=max(ret,right-left+1);//更新结果
       }

       return ret;
    }

5.第五题

LeetCode_438 找到字符串中所有的字母异位词

画图分析:

具体代码:

cpp 复制代码
vector<int> findAnagrams(string s, string p) {
        vector<int> ret;
        int hash1[26]={0};//统计字符串p中字符个数
        for(auto e:p) hash1[e-'a']++;

        int len=p.size();
        int hash2[26]={0};//统计窗口中出现字符的个数
        for(int left=0,right=0,count=0;right<s.size();right++)
        {
            char in=s[right];
            if(++hash2[in-'a']<=hash1[in-'a']) count++;//进窗口+维护count

            if(right-left+1>len)//判断
            {
                char out=s[left++];
                if(hash2[out-'a']--<=hash1[out-'a']) count--;//出窗口+维护count
            }
            //更新结果
            if(count==len) ret.push_back(left);
        }
        return ret;
    }

6.第六题

LeetCode_30 串联所有单词的子串

画图分析:

具体代码:

cpp 复制代码
 vector<int> findSubstring(string s, vector<string>& words) {
        unordered_map<string,int> hash1;//统计words中单词的次数
        for(auto e:words) hash1[e]++;

        vector<int> ret;
        int len=words[0].size(),m=words.size();
        for(int i=0;i<len;++i)//执行len次
        {
            unordered_map<string,int> hash2;
            for(int left=i,right=i,count=0;right<s.size();right+=len)
            {
                string in=s.substr(right,len);
                if(hash1.count(in) && ++hash2[in]<=hash1[in]) ++count;//进窗口+维护count

                if(right-left+1>len*m)//判断
                {
                    string out=s.substr(left,len);
                    if(hash1.count(out) && hash2[out]--<=hash1[out]) --count;//出窗口+维护count
                    left+=len;
                }

                if(count==m) ret.push_back(left);//更新结果
            }
        }

        return ret;
    }

7.第七题

LeetCode_76 最小覆盖子串

画图分析:

具体代码:

cpp 复制代码
 string minWindow(string s, string t) {
        int hash1[128]={0};//统计字符串t中每个字符出现的次数
        int kinds=0;//统计字符串t中有效字符的种类
        for(auto ch:t)
          if(hash1[ch]++==0) kinds++;

        int hash2[128]={0};//统计窗口中出现字符的次数
        int minlen=INT_MAX,begin=-1;
        for(int left=0,right=0,count=0;right<s.size();++right)
        {
            char in=s[right];
            if(++hash2[in]==hash1[in]) ++count;//进窗口+维护count
            while(count==kinds)//判断条件
            {
                if(right-left+1<minlen)//更新结果
                {
                    minlen=right-left+1;
                    begin=left;
                } 

                char out=s[left++];
                if(hash2[out]--==hash1[out]) count--;//出窗口+维护count
            }
        }

        if(begin==-1) return "";
        else return s.substr(begin,minlen);
    }
相关推荐
天勤量化大唯粉2 分钟前
基于距离的配对交易策略:捕捉价差异常偏离的均值回归机会(天勤量化代码实现)
android·开发语言·python·算法·kotlin·开源软件·策略模式
智航GIS3 分钟前
ArcGIS大师之路500技---036通俗易懂讲解克里金法
人工智能·算法·arcgis
拼好饭和她皆失5 分钟前
逆元,除法同余原理
算法·逆元·除法同余原理
leiming67 分钟前
c++ 利用模板创建一个可以储存任意类型数据的数组类
开发语言·c++·算法
TL滕9 分钟前
从0开始学算法——第二十天(简易搜索引擎)
笔记·学习·算法
cpp_250116 分钟前
P8723 [蓝桥杯 2020 省 AB3] 乘法表
数据结构·c++·算法·蓝桥杯·题解·洛谷
再__努力1点27 分钟前
【76】Haar特征的Adaboost级联人脸检测全解析及python实现
开发语言·图像处理·人工智能·python·算法·计算机视觉·人脸检测
溟洵27 分钟前
【算法C++】链表(题目列表:两数相加、两两交换链表中的节点、重排链表、合并 K 个升序链表、K 个一组翻转链表7)
数据结构·c++·算法·链表
_OP_CHEN28 分钟前
【C++数据结构进阶】玩转并查集:从原理到实战,C++ 实现与高频面试题全解析
数据结构·c++·算法
gugugu.28 分钟前
算法:hot100---128. 最长连续序列
算法