76. 最小覆盖子串
滑动窗口
import java.util.Arrays;
class Solution {
public String minWindow(String s, String t) {
if (s.length() < t.length()){
return "";
}
/**
* 滑动窗口
* 用哈希表数组记录t中每个字符在s中是否出现
* 右指针right一直右移,直到满足条件,然后记录下此时区间的边界,如果长度更小则更新l和r
*/
int[] tCount = new int[128];
int right = -1;
int l = 0;
int r = -1;
for (int i = 0; i < t.length(); i++) {
tCount[t.charAt(i)]++;
}
/**
* 左指针i从0开始,只有当区间包含所有t的字符后才会移动
*/
for (int i = 0; i < s.length() - t.length() + 1; i++) {
/**
* 只要区间没有完全包含t的元素,右指针right就不断移动
* 同时right不能越界
* 每次循环都要找出数组的最大值,时间复杂度为O(n^2)
*/
while (Arrays.stream(tCount).max().getAsInt() > 0 && right < s.length() - 1){
right++;
tCount[s.charAt(right)]--;
}
/**
* 只有当包含t的所有字符且区间长度更小且r < l时才会更新
*/
if (Arrays.stream(tCount).max().getAsInt() == 0) {
if (r < l) {
r = right;
l = i;
}
else if (r - l + 1 > right - i + 1){
r = right;
l = i;
}
}
/**
* 在左指针移动之前,要抛弃掉当前字符
*/
tCount[s.charAt(i)]++;
}
return s.substring(l, r + 1);
}
}
/**
* 时间复杂度 O(n^2)
* 空间复杂度 O(1)
*/
优化1——不用每次都找出数组最大值,同时简化判断条件
import java.util.Arrays;
class Solution {
public String minWindow(String s, String t) {
if (s.length() < t.length()){
return "";
}
/**
* 滑动窗口
* 用哈希表数组记录t中每个字符在s中是否出现
* 右指针right一直右移,直到满足条件,然后记录下此时区间的边界,如果长度更小则更新l和r
*/
int[] tCount = new int[128];
int num = t.length();
int right = -1;
int l = 0;
int r = -1;
for (int i = 0; i < t.length(); i++) {
tCount[t.charAt(i)]++;
}
/**
* 左指针i从0开始,只有当区间包含所有t的字符后才会移动
*/
for (int i = 0; i < s.length() - t.length() + 1; i++) {
/**
* 只要区间没有完全包含t的元素,右指针right就不断移动
* 同时right不能越界
* 使用一个变量num同步记录t中字符出现的次数,当次数大于0时才减1,这样就不用每次都比较tCount的最大值了
*/
while (num > 0 && right < s.length() - 1){
right++;
if (tCount[s.charAt(right)] > 0) {
num--;
}
tCount[s.charAt(right)]--;
}
/**
* 只有当包含t的所有字符且区间长度更小且r < l时才会更新
*/
if (num == 0 && (r < l || r - l + 1 > right - i + 1)) {
r = right;
l = i;
}
/**
* 在左指针移动之前,要抛弃掉当前字符,同时维护num
* 如果这个字符的次数是负数,说明其不在t中,num就不用更新
*/
if (tCount[s.charAt(i)] == 0) {
num++;
}
tCount[s.charAt(i)]++;
}
return s.substring(l, r + 1);
}
}
/**
* 时间复杂度 O(n)
* 空间复杂度 O(1)
*/
https://leetcode-cn.com/problems/minimum-window-substring/