算法18.0

76. 最小覆盖子串 - 力扣(LeetCode)

审题要理解清楚

解法1:

依旧暴力解法

枚举所有的情况 然后找到那个长度最小的字符串

解法2:优化暴力解法

这道题的算法原理有点类似算法14.0的思路 构建两个哈希表然后维护count

为了不失一般性 依旧一条横线表示题目的情况

我们找到一个区间符合情况后 开始考虑其他遍历情况(也就是双指针的移动情况)

当left右移一步 right需不需要回来再走一次

这个时候需要分情况讨论了 如果没移动前的left的那个位置的元素的个数大于hash1里面

说明这个时候 移动了也没有问题 right不需要回来再走一次

如果刚刚够或者小于 那么移动了会影响 right也没有必要回来再走一次 直接right++ 去加入新的i情况

这个时候发现 left和right都往一个方向走 联想到滑动窗口

思考滑动窗口的具体步骤不清晰的时候 可以尝试以暴力解法起手去尝试着寻找思路

判断:hash2的有效字符大于等于hash1的时候 才出窗口

优化:判断的时候 check

用变量标记一下有效字符的个数 但是这个和算法14.0中count的意义是不一样的

这里的count是比较的有效字符的种类

如果统计的是有效字符的个数的话语 是不行的 详情看下图

具体怎么统计种类 还是在进窗口和出窗口的时候维护

细节问题:

维护count的时候 发现不能用数组来维护

所以用一个新的变量kinds 表示字符的种数

解法3:类似使用算法14.0的思路

下面是题目、效果图和代码:

java 复制代码
class Solution {
    public String minWindow(String ss, String tt) {
        char[] s = ss.toCharArray();
        char[] t = tt.toCharArray();

        int[] hash1 = new int[128];
        int kinds = 0;
        for(char ch:t) {//统计t里面的频次 并找出了有多少种字符
        //    if(hash1[ch] == 0) kinds++;
        //    hash1[ch]++;
           if(hash1[ch]++ == 0) kinds++;
        }
        
        int[] hash2 = new int[128];//用来统计窗口中字符出现的频次
        int minlen = Integer.MAX_VALUE , begin = -1;
        for(int left=0,right=0,count =0;right<s.length;right++){
            
            char in = s[right];

            // hash2[in]++; 
            // if(hash2[in]==hash1[in]) count++;//如果hash1和hash2 说明我们加入了一个有效字符
             // //进窗口+维护count
            if(++hash2[in]==hash1[in]) count++; //上面两行代码可以简化成这一行 哈哈
            while(kinds==count){//判断
             //更新结果
             if(right-left+1<minlen){
                begin = left;
                minlen=right-left+1;
             }
             char out = s[left++];//移除窗口的时候记得移动一位
            //  if(hash2[out] == hash1[out]) count--;
            //  hash2[out]--;
             if(hash2[out]-- == hash1[out]) count--;//出窗口+维护count
            }
        }
        if(begin == -1) return new String();
        else return ss.substring(begin,begin+minlen);
    }
}
//xiyu251024&1#2*8
相关推荐
格林威16 分钟前
C++ 工业视觉实战:Bayer 图转 RGB 的 3 种核心算法(邻域平均、双线性、OpenCV 源码级优化)
开发语言·c++·人工智能·opencv·算法·计算机视觉·工业相机
Frostnova丶18 分钟前
LeetCode 3643.子矩阵垂直翻转算法解析
算法·leetcode·矩阵
2401_8512729919 分钟前
C++中的模板方法模式
开发语言·c++·算法
2401_8942419220 分钟前
C++中的策略模式进阶
开发语言·c++·算法
爱丽_25 分钟前
G1 深入:Region、Remembered Set、三色标记与“可预测停顿”
java·数据库·算法
sprite_雪碧26 分钟前
简单模拟问题
算法
2401_8747325327 分钟前
C++中的装饰器模式
开发语言·c++·算法
j_xxx404_30 分钟前
力扣--分治(快速排序)算法题II:数组中的第K个最大元素(Top K问题),LCR159.库存管理III
数据结构·c++·算法·leetcode
ysa05103031 分钟前
运用map优化多次查询【Kadomatsu 子序列】
数据结构·c++·笔记·算法
_饭团37 分钟前
C 语言内存函数全解析:从 memcpy 到 memcmp 的使用与模拟实现
c语言·开发语言·c++·学习·算法·面试·改行学it