已开启
最小覆盖子串-湖北工业大学-朱志强-徐承志 #146
aiyeyeyeyeye创建于 2025年6月13日
最小覆盖子串-湖北工业大学-朱志强-徐承志 #146
已开启
共 1 个文件变更+63-0
| @@ -0,0 +1,63 @@ | |||
| 1 | +import java.util.HashMap; | ||
| 2 | +import java.util.Map; | ||
| 3 | + | ||
| 4 | +class Solution { | ||
| 5 | + public String minWindow(String s, String t) { | ||
| 6 | + if (s == null || t == null || s.length() == 0 || t.length() == 0 || s.length() < t.length()) { | ||
| 7 | + return ""; | ||
| 8 | + } | ||
| 9 | + | ||
| 10 | + // 统计 t 中字符出现次数 | ||
| 11 | + Map<Character, Integer> targetMap = new HashMap<>(); | ||
| 12 | + for (char c : t.toCharArray()) { | ||
| 13 | + targetMap.put(c, targetMap.getOrDefault(c, 0) + 1); | ||
| 14 | + } | ||
| 15 | + | ||
| 16 | + int required = targetMap.size(); // 需要匹配的字符种类数 | ||
| 17 | + int formed = 0; // 当前窗口中已匹配的字符种类数 | ||
| 18 | + | ||
| 19 | + // 滑动窗口指针 | ||
| 20 | + int left = 0; | ||
| 21 | + int right = 0; | ||
| 22 | + | ||
| 23 | + // 记录最小窗口的信息 | ||
| 24 | + int minLen = Integer.MAX_VALUE; | ||
| 25 | + int minLeft = 0; | ||
| 26 | + | ||
| 27 | + // 统计窗口中字符出现次数 | ||
| 28 | + Map<Character, Integer> windowMap = new HashMap<>(); | ||
| 29 | + | ||
| 30 | + while (right < s.length()) { | ||
| 31 | + char c = s.charAt(right); | ||
| 32 | + windowMap.put(c, windowMap.getOrDefault(c, 0) + 1); | ||
| 33 | + | ||
| 34 | + // 如果当前字符在 t 中,并且窗口中的数量达到了 t 中的数量 | ||
| 35 | + if (targetMap.containsKey(c) && windowMap.get(c).intValue() == targetMap.get(c).intValue()) { | ||
| 36 | + formed++; | ||
| 37 | + } | ||
| 38 | + | ||
| 39 | + // 尝试收缩左边界 | ||
| 40 | + while (left <= right && formed == required) { | ||
| 41 | + c = s.charAt(left); | ||
| 42 | + | ||
| 43 | + // 更新最小窗口 | ||
| 44 | + if (right - left + 1 < minLen) { | ||
| 45 | + minLen = right - left + 1; | ||
| 46 | + minLeft = left; | ||
| 47 | + } | ||
| 48 | + | ||
| 49 | + // 左边界移动,更新窗口统计 | ||
| 50 | + windowMap.put(c, windowMap.get(c) - 1); | ||
| 51 | + if (targetMap.containsKey(c) && windowMap.get(c) < targetMap.get(c)) { | ||
| 52 | + formed--; | ||
| 53 | + } | ||
| 54 | + | ||
| 55 | + left++; | ||
| 56 | + } | ||
| 57 | + | ||
| 58 | + right++; | ||
| 59 | + } | ||
| 60 | + | ||
| 61 | + return minLen == Integer.MAX_VALUE ? "" : s.substring(minLeft, minLeft + minLen); | ||
| 62 | + } | ||
| 63 | +} | ||