首页 > 其他分享 >最小覆盖子串

最小覆盖子串

时间:2024-12-23 23:52:59浏览次数:4  
标签:子串 right 窗口 覆盖 nums 最小 cntMap left

 

 

滑动窗口算法的思路是这样:

  • 1、我们在字符串 S 中使用双指针中的左右指针技巧,初始化 left = right = 0,把索引左闭右开区间 [left, right) 称为一个「窗口」。

  • 2、我们先不断地增加 right 指针扩大窗口 [left, right),直到窗口中的字符串符合要求(包含了 T 中的所有字符)。

  • 3、此时,我们停止增加 right,转而不断增加 left 指针缩小窗口 [left, right),直到窗口中的字符串不再符合要求(不包含 T 中的所有字符了)。同时,每次增加 left,我们都要更新一轮结果。

  • 4、重复第 2 和第 3 步,直到 right 到达字符串 S 的尽头。

 

使用cntMap优化子串判断条件,统计每个子串需要出现的次数,以及需要几个不同的字母nums

 

时间复杂度:O(m+n),m,n分别为字符串m和n的长度

空间复杂度:O(n)

func getSubStr(s, t string) string {
    cntMap := make(map[byte]int, len(t))
    nums := 0
    for _, c := range []byte(t) {
        if cntMap[c] == 0 {
            nums++ // 统计t字符串中有几种字母出现
        }
        cntMap[c]++ //记录t字符串中每个字母需要出现的次数
    }

    ans1, ans2 := -1, len(s) //初始化最优解的左右窗口下标
    left := 0                //从[0,0]区间开始,右指针不断右移
    for right, c := range []byte(s) {
        cntMap[c]--         // 对应次数减1
        if cntMap[c] == 0 { //该字母满足出现次数要求
            nums-- //子串需要的字母总数减少一个
        }
        for nums == 0 { // 开始找最优解,直到子串字母需要出现的次数都满足,
            if right-left < ans2-ans1 { // 找到更短的子串
                ans1, ans2 = left, right // 记录此时的左右端点
            }
            x := s[left]        // 左端点字母
            if cntMap[x] == 0 { // x 移出窗口之前,检查出现次数,x字符移走后,次数要+1
                nums++
            }
            cntMap[x]++ // 左端点字母移出子串
            left++
        }
    }
    //左指针没有移动过,最大化窗口也不满足条件,没有找到
    if ans1 < 0 {
        return ""
    }
    return s[ans1 : ans2+1]
}

 

标签:子串,right,窗口,覆盖,nums,最小,cntMap,left
From: https://www.cnblogs.com/-citywall123/p/18625309

相关文章

  • Java代码覆盖率super-jacoco
    开源项目地址https://gitee.com/didiopensource/super-jacoco项目流程项目架构部署步骤注意:一定要用Linux服务器部署,不要用Windows准备Linux服务器环境安装好JDK1.8安装好git安装和配置好Maven3.6,或3.6以下安装MySQL数据库(尽量不用8版本,就用5.7、5.8版本)拉取super-......
  • 基于覆盖选址理论的两阶段随机规划模型
    基于覆盖选址理论的两阶段随机规划模型是一种结合了覆盖选址理论与随机规划方法的选址决策模型。以下是对该模型的详细解析:一、覆盖选址理论覆盖选址问题主要分为集覆盖问题和最大覆盖问题两类:集覆盖问题:研究在满足覆盖所有需求点的条件下,寻求所建设施个数或建设成本最小化的......
  • 【字符串】-Lc5-最长回文子串(中心扩展法)
    写在前面  最近想复习一下数据结构与算法相关的内容,找一些题来做一做。如有更好思路,欢迎指正。目录写在前面一、场景描述二、具体步骤1.环境说明2.代码写在后面一、场景描述  最长回文子串。给你一个字符串s,找到s中最长的回文子串。定义:如果字符串的反......
  • 302 最小循环覆盖
    //302最小循环覆盖.cpp:此文件包含"main"函数。程序执行将在此处开始并结束。///*http://oj.daimayuan.top/course/22/problem/909给你一个字符串a,你需要求出这个字符串的最小循环覆盖的长度。b是a的最小循环覆盖,当且仅当a是通过b复制多次并连接后得到的字符......
  • 最小生成树相关技术
    注意只有连通图才有生成树,图不连通就只有生成森林。最小生成树的板子Kruskal基本思想是按边权从小到大加边,是贪心思想。时间复杂度\(O(m\logm)\)。板子sort(e+1,e+tot+1,cmp);for(inti=1;i<=tot;++i){ intu=e[i].u,v=e[i].v; u=find(u),v=find(v); if(u==v)continu......
  • 写一个方法找出两个数的最小公倍数
    在前端开发中,你可以使用JavaScript来写一个方法找出两个数的最小公倍数(LeastCommonMultiple,LCM)。最小公倍数可以通过两数的乘积除以它们的最大公约数(GreatestCommonDivisor,GCD)来得到。以下是一个简单的JavaScript函数,用于计算两个数的最小公倍数:functiongcd(a,b){......
  • Java学习,方法覆盖
    Java方法覆盖是面向对象编程中的一个重要概念,它允许子类提供一个特定实现,该实现将覆盖(或重写)父类中已有方法。通过方法覆盖,子类可以自定义或扩展从父类继承的行为。方法重载与方法覆盖区别:方法重载(Overloading):两个方法的方法名相同,但参数不一致,可以说一个方法是另一个方法......
  • 【编译原理】编译原理知识点汇总·词法分析器(正则式到NFA、NFA到DFA、DFA最小化)
    ......
  • Averaging Weights Leads to Wider Optima and Better Generalization(SWA2018-2019)平
    第一部分:解决的问题论文解决的是深度神经网络优化过程中模型的泛化能力提升问题。具体来说:背景问题:在深度学习中,SGD(随机梯度下降)及其变种是主要的优化方法,但其找到的解通常在权重空间中是“尖锐(参数稍微变一点损失函数就会变化很大)的”(sharpminima),对模型泛化性能有负面影......
  • 深度学习之平坦最小化
    第一部分:基础定义平坦最小化(PlateauMinimization)通常出现在数学优化、图像处理和信号处理领域,指的是一种优化方法或目标,其目的是找到在某些意义下“平坦”的解,同时对目标函数或某些能量函数进行最小化。平坦最小化的核心思想是:不仅仅关注优化问题的极值,还特别关注优化解在某......