算法(滑动窗口四)

1.串联所有单词的子串

   

给定一个字符串 s 和一个字符串数组 words words 中所有字符串 长度相同

 s 中的 串联子串 是指一个包含  words 中所有字符串以任意顺序排列连接起来的子串。

  • 例如,如果 words = ["ab","cd","ef"], 那么 "abcdef", "abefcd""cdabef", "cdefab""efabcd", 和 "efcdab" 都是串联子串。 "acdbef" 不是串联子串,因为他不是任何 words 排列的连接。

返回所有串联子串在 s 中的开始索引。你可以以 任意顺序 返回答案。

示例 1:

输入:s = "barfoothefoobarman", words = ["foo","bar"]
输出:[0,9]
解释:因为 words.length == 2 同时 words[i].length == 3,连接的子字符串的长度必须为 6。
子串 "barfoo" 开始位置是 0。它是 words 中以 ["bar","foo"] 顺序排列的连接。
子串 "foobar" 开始位置是 9。它是 words 中以 ["foo","bar"] 顺序排列的连接。
输出顺序无关紧要。返回 [9,0] 也是可以的。

示例 2:

输入:s = "wordgoodgoodgoodbestword", words = ["word","good","best","word"]
输出:[]
解释:因为 words.length == 4 并且 words[i].length == 4,所以串联子串的长度必须为 16。
s 中没有子串长度为 16 并且等于 words 的任何顺序排列的连接。
所以我们返回一个空数组。

示例 3:

输入:s = "barfoofoobarthefoobarman", words = ["bar","foo","the"]
输出:[6,9,12]
解释:因为 words.length == 3 并且 words[i].length == 3,所以串联子串的长度必须为 9。
子串 "foobarthe" 开始位置是 6。它是 words 中以 ["foo","bar","the"] 顺序排列的连接。
子串 "barthefoo" 开始位置是 9。它是 words 中以 ["bar","the","foo"] 顺序排列的连接。
子串 "thefoobar" 开始位置是 12。它是 words 中以 ["the","foo","bar"] 顺序排列的连接。

算法原理

我们随便来看一个例子 输入:s = "barfoofoobarthefoobarman", words = ["bar","foo","the"]

我们把bar 看成一个a,foo看成一个b,the看成一个c

 这个题的s就可以看成一串 abbacvad

这样这个题就变成一个找出字符串你的异位字符,变成跟我们做的上个题是一样的

这道题我们要熟练的运用容器以及哈希表和List表

这道题我们right-left的长度不能大于words数组的长度,即单词的长度

由于我们不确定从哪里开始是我们想要找的单词的首字母,我们需要遍历单个单词的每个字母如下图所示

我们要对一个单词遍历这个单词的每个字母,所以我们要套两层for循环

第一层for循环就是   for(int i=0;i<len;i++) 表示words单词里面每个单词的长度

1.定义left=i,right=i 还需要定义一个count用来记录单词的数量定义两个哈希表,一个哈希表hash1用来记录words数组里面单词的个数,一个哈希表hash2用来记录s表内的单词,用len表示words单词的长度

2.我们的起始位置是right=i,终止位置时 right+len 每次向后移动都是移动len的长度

3.我们首先需要进窗口,用in来接受进入窗口的单词,然后我们判断进来窗口的单是否在 hash1中存在 存在就count++ 

3,当我们一直向后判断,当right-left的值>words里面字符的m(m表示单词的个数)*len了 说明此时我们应该出窗口了 在出窗口前我们需要判断出窗口的单词是否存在于hash1表中,存在我们就count--

然后left+len判断下一个单词

4.当count==m 说明此时正是我们要找的子串,我们输出left的值

代码如下

class Solution {public List<Integer> findSubstring(String s, String[] words) {List<Integer>ret=new ArrayList();Map<String,Integer>hash1=new HashMap<String,Integer>();for(String str:words)hash1.put(str,hash1.getOrDefault(str,0)+1);int len=words[0].length(),m=words.length;for(int i=0;i<len;i++){Map<String,Integer>hash2=new HashMap<String,Integer>();for(int left=i,right=i,count=0;right+len<=s.length();right+=len){String in=s.substring(right,right+len);hash2.put(in,hash2.getOrDefault(in,0)+1);if(hash2.get(in)<=hash1.getOrDefault(in,0))count++;if(right-left+1>len*m){String out=s.substring(left,left+len);if(hash2.get(out)<=hash1.getOrDefault(out,0))count--;hash2.put(out,hash2.get(out)-1);left+=len;}if(count==m){ret.add(left);}}}return ret;}
}

2.最小覆盖子串

  

给你一个字符串 s 、一个字符串 t 。返回 s 中涵盖 t 所有字符的最小子串。如果 s 中不存在涵盖 t 所有字符的子串,则返回空字符串 "" 。

注意:

  • 对于 t 中重复字符,我们寻找的子字符串中该字符数量必须不少于 t 中该字符数量。
  • 如果 s 中存在这样的子串,我们保证它是唯一的答案。

示例 1:

输入:s = "ADOBECODEBANC", t = "ABC"
输出:"BANC"
解释:最小覆盖子串 "BANC" 包含来自字符串 t 的 'A'、'B' 和 'C'。

示例 2:

输入:s = "a", t = "a"
输出:"a"
解释:整个字符串 s 是最小覆盖子串。

示例 3:

输入: s = "a", t = "aa"
输出: ""
解释: t 中两个字符 'a' 均应包含在 s 的子串中,
因此没有符合条件的子字符串,返回空字符串。

   程序解法:

      1.暴力解法:通过暴力枚举,枚举出所有结果,然后比对所有结果那个子串最短

      2.滑动窗口+哈希表

  算法原理 

这个题我们依旧用滑动窗口来做,并且用数组来模拟哈希表

如图我们有以下的一个字符串,我们要找的是abc的最小子串,

1.我们给字符串和abc串各创建一个数组

    int[]hash1=new int[128];

int[] hash2=new int[128];

hash1用来存放abc,hash2用来存放长的字符串

我们来统计hash1中的个数,这里使用统计个数的方式不可取,因为长的字符串中有可能有多个一样的字符,我们就取第一次出现的字符为新的字符,就是取种类的个数

 for(char ch:t){if(hash1[ch]==0)kinds++;hash1[ch]++;}
 

2.采用滑动窗口的方式

        定义left=0,right=0,count=0;

    我们首先进入窗口,进窗口之后判断hash2[right]==hash1[right] 相等就++ 

   

 int minlen=Integer.MAX_VALUE,begin=-1;for(int left=0,right=0,count=0;right<ss.length();right++){char in=s[right];hash2[in]++;if(hash1[in]==hash2[in])count++;

然后当kind和count相等时 我们更新结果,取出当前right-left+1的值,和开始的值

 int minlen=Integer.MAX_VALUE,begin=-1;
while(kinds==count){if(right-left+1<minlen){minlen=right-left+1;begin=left;}

3.更新完结果后我们出窗口

  

 char out=s[left];left++;if(hash1[out]==hash2[out]) count--;hash2[out]--;

最后代码如下

class minWindow {public String minWindow1  (String ss, String tt) {char s[]=ss.toCharArray();char t[]=tt.toCharArray();int[]hash1=new int[128];int[] hash2=new int[128];int kinds=0;for(char ch:t){if(hash1[ch]==0)kinds++;hash1[ch]++;}int minlen=Integer.MAX_VALUE,begin=-1;for(int left=0,right=0,count=0;right<ss.length();right++){char in=s[right];hash2[in]++;if(hash1[in]==hash2[in])count++;while(kinds==count){if(right-left+1<minlen){minlen=right-left+1;begin=left;}char out=s[left];left++;if(hash1[out]==hash2[out]) count--;hash2[out]--;}}if(begin==-1)return new String();else return ss.substring(begin,begin+minlen);}public static void main(String[] args) {minWindow minWindow=new minWindow();String s="ADOBECODEBANC";String t="AABC";String result= minWindow.minWindow1(s,t);System.out.println(result);}
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/793914.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【NLP练习】中文文本分类-Pytorch实现

中文文本分类-Pytorch实现 &#x1f368; 本文为&#x1f517;365天深度学习训练营 中的学习记录博客&#x1f356; 原作者&#xff1a;K同学啊 一、准备工作 1. 任务说明 本次使用Pytorch实现中文文本分类。主要代码与文本分类代码基本一致&#xff0c;不同的是本次任务使用…

Ubuntu系统安装NVIDIA 与pytorch

#安装Ubuntu https://zhuanlan.zhihu.com/p/355314438 #安装vm tools https://blog.csdn.net/weixin_45502414/article/details/130151842 https://blog.csdn.net/weixin_59605625/article/details/128750037 若安装正常使用,显示屏字体与复制粘贴都能解决&#xff0c;如果不…

FAS-Net

感想 图的下标弄不好&#xff0c;且作者未提供代码。AAAI的质量也就这样吧

Web Component 组件库有什么优势

前言 前端目前比较主流的框架有 react&#xff0c;vuejs&#xff0c;angular 等。 我们通常去搭建组件库的时候都是基于某一种框架去搭建&#xff0c;比如 ant-design 是基于 react 搭建的UI组件库&#xff0c;而 element-plus 则是基于 vuejs 搭建的组件库。 可能你有这种体…

Vue框架介绍简介

Vue.js&#xff0c;通常简称为Vue&#xff0c;是一个用于构建用户界面的渐进式框架。它发布于2014年2月&#xff0c;由Evan You设计并开发。Vue被设计为可以自底向上逐层应用&#xff0c;这使得开发者可以根据项目的需求灵活地使用Vue。无论是构建简单的轻量级应用&#xff0c;…

Transformer的代码实现 day03(Positional Encoding)

Positional Encoding的理论部分 注意力机制是不含有位置信息&#xff0c;这也就表明&#xff1a;“我爱你”&#xff0c;“你爱我”这两者没有区别&#xff0c;而在现实世界中&#xff0c;这两者有区别。所以位置编码是在进行注意力计算之前&#xff0c;给输入加上一个位置信息…

【RISC-V 指令集】RISC-V 向量V扩展指令集介绍(五)- 向量加载和存储

1. 引言 以下是《riscv-v-spec-1.0.pdf》文档的关键内容&#xff1a; 这是一份关于向量扩展的详细技术文档&#xff0c;内容覆盖了向量指令集的多个关键方面&#xff0c;如向量寄存器状态映射、向量指令格式、向量加载和存储操作、向量内存对齐约束、向量内存一致性模型、向量…

Redis -- 缓存穿透问题解决思路

缓存穿透 &#xff1a;缓存穿透是指客户端请求的数据在缓存中和数据库中都不存在&#xff0c;这样缓存永远不会生效&#xff0c;这些请求都会打到数据库。 常见的解决方案有两种&#xff1a; 缓存空对象 优点&#xff1a;实现简单&#xff0c;维护方便 缺点&#xff1a; 额外…

解密ChatGPT技巧:提升学术论文写作水平

ChatGPT无限次数:点击直达 解密ChatGPT技巧&#xff1a;提升学术论文写作水平 在当今信息爆炸的时代&#xff0c;学术论文写作已经成为学术研究者们日常不可或缺的任务之一。而借助人工智能技术&#xff0c;特别是最新的语言模型ChatGPT&#xff0c;可以极大地提升论文写作的效…

【JavaSE】接口 详解(上)

前言 本篇会讲到Java中接口内容&#xff0c;概念和注意点可能比较多&#xff0c;需要耐心多看几遍&#xff0c;我尽可能的使用经典的例子帮助大家理解~ 欢迎关注个人主页&#xff1a;逸狼 创造不易&#xff0c;可以点点赞吗~ 如有错误&#xff0c;欢迎指出~ 目录 前言 接口 语法…

RabbitMQ面经 手敲浓缩版

保证可靠性 生产者 本地事务完成和消息发送同时完成 通过事务消息完成 重写confirm在里面做逻辑处理 确保发送成功&#xff08;不成功就放入到重试队列&#xff09; MQ 打开持久化确保消息不会丢失 消费者 改成手动回应 不重复消费 生产者 保证不重复发送消息 消费者…

pta 1086 就不告诉你

1086 就不告诉你 分数 15 全屏浏览 切换布局 作者 CHEN, Yue 单位 浙江大学 做作业的时候&#xff0c;邻座的小盆友问你&#xff1a;“五乘以七等于多少&#xff1f;”你应该不失礼貌地围笑着告诉他&#xff1a;“五十三。”本题就要求你&#xff0c;对任何一对给定的正整数…

新手开抖店:选品过后如何有效对接达人?这些方法100%有效!

哈喽~我是电商月月 要说做抖音小店最主要的是什么&#xff1f;那当然是找品了 那出单最快的方法是什么&#xff1f;无疑是达人带货了&#xff01; 但新手店铺没销量&#xff0c;没体验分&#xff0c;没好评怎么能让达人同意帮我们带货呢&#xff1f; 方法其实很简单&#x…

“双碳”目标下资源环境中的可计算一般均衡(CGE)模型应用

我国政府承诺在2030年实现“碳达峰”&#xff0c;2060年实现“碳中和”&#xff0c;这就是“双碳”目标。为了实现这一目标就必须应用各种二氧化碳排放量很高技术的替代技术&#xff0c;不仅需要考虑技术上的可靠性&#xff0c;也需要考虑经济上的可行性。可计算一般均衡模型&a…

ChatGPT新手指南:如何应用于学术论文撰写

ChatGPT无限次数:点击直达 html ChatGPT新手指南&#xff1a;如何应用于学术论文撰写 在当今信息爆炸的时代&#xff0c;学术论文写作是许多研究人员、学生和学者每天都要面对的任务。随着人工智能技术的不断发展&#xff0c;如何利用自然语言生成模型来辅助学术论文的撰写…

AI预测福彩3D第26弹【2024年4月4日预测--第4套算法重新开始计算第11次测试】

今天清明节假日&#xff0c;一会要外出&#xff0c;可能要晚点回来。咱们尽早先把预测数据跑完&#xff0c;把结果发出来供各位彩友参考。合并下算法&#xff0c;3D的预测以后将重点测试本套算法&#xff0c;因为本套算法的命中率较高。以后有时间的话会在第二篇文章中发布排列…

JDK版本发布历史

以下是Java Development Kit&#xff08;JDK&#xff09;主要版本的发布历史&#xff1a; JDK 1.0&#xff1a;1996年1月23日发布&#xff0c;是Java的首个正式版本。JDK 1.1&#xff1a;1997年2月19日发布&#xff0c;引入了内部类、反射、JAR文件等新特性。JDK 1.2&#xff…

UTONMOS:AI+Web3+元宇宙数字化“三位一体”将触发经济新爆点

人工智能、元宇宙、Web3&#xff0c;被称为数字化的“三位一体”&#xff0c;如何看待这三大技术所扮演的角色&#xff1f; 3月24日&#xff0c;2024全球开发者先锋大会“数字化的三位一体——人工智能、元宇宙、Web3.0”论坛在上海漕河泾开发区举行&#xff0c;首次提出&…

深入探索MySQL:成本模型解析与查询性能优化,及未来深度学习与AI模型的应用展望

码到三十五 &#xff1a; 个人主页 在数据库管理系统中&#xff0c;查询优化器是一个至关重要的组件&#xff0c;它负责将用户提交的SQL查询转换为高效的执行计划。在MySQL中&#xff0c;查询优化器使用了一个称为“成本模型”的机制来评估不同执行计划的优劣&#xff0c;并选择…

网络安全 | 什么是负载均衡器?

关注WX&#xff1a; CodingTechWork 介绍 负载均衡是在多个服务器之间有效分配网络流量的过程。负载均衡的目的是优化应用程序的可用性&#xff0c;并确保良好的终端用户体验。负载均衡可协助高流量网站和云计算应用程序应对数百万个用户请求&#xff0c;从而保证客户请求不会…