leetcode上大概10道滑动窗口题目,难度为medium/hard

模板:

思路:

图片.png
复杂度为O(n)

模板:

  1. /* 滑动窗口算法框架 */
  2. void slidingWindow(string s, string t) {
  3. unordered_map<char, int> need, window;
  4. for (char c : t) need[c]++;
  5. int left = 0, right = 0;
  6. int valid = 0;
  7. while (right < s.size()) {
  8. // c 是将移入窗口的字符
  9. char c = s[right];
  10. // 右移窗口
  11. right++;
  12. // 进行窗口内数据的一系列更新
  13. ...
  14. /*** debug 输出的位置 ***/
  15. printf("window: [%d, %d)\n", left, right);
  16. /********************/
  17. // 判断左侧窗口是否要收缩
  18. while (window needs shrink) {
  19. // d 是将移出窗口的字符
  20. char d = s[left];
  21. // 左移窗口
  22. left++;
  23. // 进行窗口内数据的一系列更新
  24. ...
  25. }
  26. }
  27. }

例题

经典题目问题1:最小子串

图片.png

  1. function minWindow(str,target){
  2. let need = {},window={};
  3. for(let t of target){
  4. need[t] = need[t]++
  5. }
  6. //valid变量的设置!!!
  7. let left = 0,right=0,valid=0;
  8. //len长度的设置!!!
  9. let start=0,len = Number.Max_Integer;
  10. while(right<str.length){
  11. let s = str[right];
  12. right++;
  13. if(need[s]){
  14. window[s]++
  15. if(window[s]===need[s]){
  16. valid++;
  17. }
  18. }
  19. while(valid===Object.keys().length){
  20. //取start len的值,此处非常巧妙!!!!保证了最小长度
  21. if(right-left<len){
  22. start = left;
  23. len = right-left;
  24. }
  25. const c = str[left];
  26. left++;
  27. if(need[c]){
  28. if(window[c]===need[d]){
  29. valid--;
  30. window[c]--;
  31. }
  32. }
  33. }
  34. }
  35. return len==Number.Max_Integer?'':str.substring(start,len);
  36. }

问题2:字符串排列

图片.png

  1. // 判断 s 中是否存在 t 的排列
  2. bool checkInclusion(string t, string s) {
  3. unordered_map<char, int> need, window;
  4. for (char c : t) need[c]++;
  5. int left = 0, right = 0;
  6. int valid = 0;
  7. while (right < s.size()) {
  8. char c = s[right];
  9. right++;
  10. // 进行窗口内数据的一系列更新
  11. if (need.count(c)) {
  12. window[c]++;
  13. if (window[c] == need[c])
  14. valid++;
  15. }
  16. // 判断左侧窗口是否要收缩
  17. while (right - left >= t.size()) {
  18. // 在这里判断是否找到了合法的子串
  19. if (valid == need.size())
  20. return true;
  21. char d = s[left];
  22. left++;
  23. // 进行窗口内数据的一系列更新
  24. if (need.count(d)) {
  25. if (window[d] == need[d])
  26. valid--;
  27. window[d]--;
  28. }
  29. }
  30. }
  31. // 未找到符合条件的子串
  32. return false;
  33. }

疑问:如果如果字母不相邻怎么办?

问题3:找所以字母异位词

图片.png

问题4:最长无重复子串

图片.png