滑动窗口主要用于解决 连续子数组 / 子串 问题。
核心思想:
用左右两个指针维护一个连续区间,右边扩张,左边根据条件收缩,避免重复计算。
1. 定长滑动窗口
窗口长度固定为 k。
核心流程:
右边加入
→ 窗口形成
→ 更新答案
→ 左边移出
Python 模板:
left = 0
sums = 0
for right, x in enumerate(nums):
sums += x
if right + 1 >= k: # 此时窗口长度为 k,更新答案
sums -= nums[left]
left += 1
也可以直接计算左端点:
for right, x in enumerate(nums):
sums += x
if right + 1 >= k: # 更新答案
left = right + 1 - k
sums -= nums[left]
常见题型:
- 长度为
k 的最大 / 最小子数组和
- 固定长度窗口统计
- 长度为
k 且元素互不相同
2. 不定长滑动窗口
窗口长度会根据条件动态变化。
核心流程:
右边扩张
→ 窗口不合法
→ 左边收缩
→ 重新合法
→ 更新答案
Python 模板:
left = 0
for right, x in enumerate(nums):
# x 加入窗口
while 窗口不合法:
# nums[left] 移出窗口
left += 1
# 更新答案
例如维护窗口和:
left = 0sums = 0
for right, x in enumerate(nums):
sums += x
while sums > target:
sums -= nums[left]
left += 1
ans = max(ans, right - left + 1)
3. 哈希表 + 滑动窗口
遇到重复元素、出现次数问题时,经常搭配字典:
from collections import defaultdictcnt = defaultdict(int)
left = 0
for right, x in enumerate(nums):
cnt[x] += 1
while cnt[x] > 1:
cnt[nums[left]] -= 1
left += 1
ans = max(ans, right - left + 1)
这个思路常用于:
最长无重复子串
每个元素最多出现 k 次
窗口中不同元素数量限制
总结
定长滑动窗口重点:
什么时候窗口形成。
不定长滑动窗口重点:
什么时候窗口不合法。
做题时主要想清楚:
窗口维护什么?
什么时候移动 left?
什么时候更新答案?