字符串的排列
难度:
标签:
题目描述
代码结果
运行时间: 66 ms, 内存: 16.1 MB
/*
* 思路:
* 使用Java Stream API简化代码,通过流的方式处理字符频率和滑动窗口。
* 1. 使用Stream构建s1的字符频率数组。
* 2. 使用IntStream创建滑动窗口并更新窗口字符频率。
* 3. 每次窗口移动后,比较两个频率数组是否相等。
*/
import java.util.Arrays;
import java.util.stream.IntStream;
public class Solution {
public boolean checkInclusion(String s1, String s2) {
if (s1.length() > s2.length()) return false;
int[] freq1 = s1.chars().map(c -> c - 'a').collect(() -> new int[26], (arr, c) -> arr[c]++, (arr1, arr2) -> {
for (int i = 0; i < arr1.length; i++) arr1[i] += arr2[i];
});
int[] freq2 = new int[26];
IntStream.range(0, s1.length()).forEach(i -> freq2[s2.charAt(i) - 'a']++);
return IntStream.range(0, s2.length() - s1.length() + 1)
.anyMatch(i -> {
if (i > 0) {
freq2[s2.charAt(i - 1) - 'a']--;
freq2[s2.charAt(i + s1.length() - 1) - 'a']++;
}
return Arrays.equals(freq1, freq2);
});
}
}
解释
方法:
这个题解使用了滑动窗口的思路。首先用 Counter 统计 s1 中每个字符出现的次数,作为需要满足的条件。然后在 s2 上滑动窗口,扩张和收缩窗口,并统计窗口内每个字符的出现次数。当窗口内某个字符的出现次数与 s1 中对应的次数相等时,说明找到了一个符合条件的字符。当所有字符都符合条件,且窗口大小等于 s1 的长度时,说明找到了一个 s1 的排列,返回 True。如果滑动到 s2 的末尾还没找到,则返回 False。
时间复杂度:
O(n)
空间复杂度:
O(1)
代码细节讲解
🦆
为什么在判断窗口内字符数量后,需要比较窗口的大小和s1的长度是否一致?
▷🦆
在代码中,如果s2中的字符不在s1中,为什么需要重置窗口而不是简单地移动左指针?
▷🦆
如何确保窗口内的字符顺序不会影响判断结果,即只需关注字符的数量而非其排列顺序?
▷🦆
在滑动窗口算法中,valid变量的作用是什么,它如何帮助我们判断当前窗口是否可能包含s1的一个排列?
▷相关问题
最小覆盖子串
给你一个字符串 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 的子串中, 因此没有符合条件的子字符串,返回空字符串。
提示:
m == s.length
n == t.length
1 <= m, n <= 105
s
和t
由英文字母组成
进阶:你能设计一个在
o(m+n)
时间内解决此问题的算法吗?找到字符串中所有字母异位词
给定两个字符串 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" 的异位词。
提示:
1 <= s.length, p.length <= 3 * 104
s
和p
仅包含小写字母