难度中等702收藏分享切换为英文接收动态反馈
给定两个字符串 s
和 p
,找到 s
中所有 p
的 异位词 的子串,返回这些子串的起始索引。不考虑答案输出的顺序。
异位词 指由相同字母重排列形成的字符串(包括相同的字符串)。
示例 1:
输入: s = "cbaebabacd", p = "abc" 输出: [0,6] 解释: 起始索引等于 0 的子串是 "cba", 它是 "abc" 的异位词。 起始索引等于 6 的子串是 "bac", 它是 "abc" 的异位词。
示例 2:
输入: s = "abab", p = "ab" 输出: [0,1,2] 解释: 起始索引等于 0 的子串是 "ab", 它是 "ab" 的异位词。 起始索引等于 1 的子串是 "ba", 它是 "ab" 的异位词。 起始索引等于 2 的子串是 "ab", 它是 "ab" 的异位词
解题思路:
根据题目要求,我们需要在字符串 s 寻找字符串 p 的异位词。因为字符串 p 的异位词的长度一定与字符串 p 的长度相同,所以我们可以在字符串 s中构造一个长度为与字符串 p 的长度相同的滑动窗口,并在滑动中维护窗口中每种字母的数量;当窗口中每种字母的数量与字符串 p 中每种字母的数量相同时,则说明当前窗口为字符串 p 的异位词。
这是我第一次的解法:将字符串p的字母转为数字,与字符串s中的字串进行比较
public class LC0438 {
public static List<Integer> findAnagrams(String s, String p) {
List<Integer> list=new ArrayList<>();
if(p.length()>s.length())return list;
int count=0;
for(int i=0;i<p.length();i++){
count+=p.charAt(i)-96;
}
for(int i=0;i<s.length();i++){
//当字符串s的剩余长度小于字符串p返回list
if(s.length()-i<p.length())return list;
int num=0;
for(int j=i;j<i+p.length();j++){
num+=s.charAt(j)-96;
//当num大于count时直接break
if(num>count)break;
}
//当num等于count则是异位词
if(num==count){
list.add(i);
}
}
return list;
}
public static void main(String[] args) {
Scanner sc=new Scanner(System.in);
String s=sc.nextLine();
String p=sc.nextLine();
System.out.println(findAnagrams(s,p));
}
}
但是用例是af,be时通过不了,我又加了一些判断,但是当字符串非常长的时候也会出现问题
这是我第二次的解法:用数组中对应的各字母出现次数进行比较
public List<Integer> findAnagrams(String s, String p) {
int sLen=s.length();int pLen=p.length();
List<Integer> list=new ArrayList<>();
if(sLen<pLen)return list;
int[] pCount=new int[26];
int dff=0;
for(char c:p.toCharArray()){
pCount[c-'a']+=1;
}
for(int i=0;i<s.length();i++){
if(s.length()-i<p.length())return list;
if(!p.contains(s.substring(i,i+1)))continue;
int[] sCount=new int[26];
for(int j=i;j<i+p.length();j++){
if(++sCount[s.charAt(j)-'a']>pCount[s.charAt(j)-'a']){
break;
}
}
if(Arrays.equals(pCount,sCount))list.add(i);
}
return list;
}
我总共提交了三次,每次都加上了一些提前结束的判断,其中一些细节:
1.当s字符串剩余长度不足时返回list
2.当前增加的数组中值超过数组P中对应的值结束当前循环
平常写算法要多想不同方法,拓宽自己思路。竞赛或面试时才不容易思想掉线
同时多扣细节,竞赛时复杂度过高过不了的地方稍加优化可能就通过了,同时细节也是面试题算法的加分点