题目
类型:滑动窗口
解题思路
1、异位词的长度一定与字符串 p 的长度相同,所以我们可以在字符串 s 中构造一个长度为与字符串 p 的长度相同的滑动窗口
2、统计滑动窗口和字符串 p 中每种字母数量的差;并引入变量 differ 来记录当前窗口与字符串 p 中数量不同的字母的个数,并在滑动窗口的过程中维护它。
3、在判断滑动窗口中每种字母的数量与字符串 p中每种字母的数量是否相同时,只需要判断differ 是否为零即可。
4、当字符串 s 的长度小于字符串 p 的长度时,字符串 s 中一定不存在字符串 p 的异位词。但是因为字符串 s 中无法构造长度与字符串 p 的长度相同的窗口,所以这种情况需要单独处理。
代码
class Solution {
public List<Integer> findAnagrams(String s, String p) {
List<Integer> ans = new ArrayList<>();
int n = s.length(), m = p.length();
int[] cnt = new int[26];
//遍历目标字符串,统计每个字母的个数,使用cnt数组存放
for (int i = 0; i < m; i++) {
cnt[p.charAt(i) - 'a']++;
}
int a = 0;
//用a统计目标字符串不同的字母数量
for (int i = 0; i < 26; i++) {
if (cnt[i] != 0) {
a++;
}
}
for (int l = 0, r = 0, b = 0; r < n; r++) {
// 往窗口增加字符,进行词频的抵消操作,如果抵消后词频为 0,说明有一个新的字符词频与 p 完全相等
if (--cnt[s.charAt(r) - 'a'] == 0) {
b++;
}
// 若窗口长度超过规定,将窗口左端点右移,执行词频恢复操作,如果恢复后词频为 1(恢复前为 0),说明少了一个词频与 p 完全性相等的字符
if (r - l + 1 > m && ++cnt[s.charAt(l++) - 'a'] == 1){
b--;
}
if (b == a) {
ans.add(l);
}
}
return ans;
}
}