首先我们先来理解题目要求:
通过题目要求我们需要找到一个最短的子串,其中包含所有三种类型的灯(R、G、B)。如果无法满足这样的字串,返回-1。
因此我们对于数据结构的选择:
哈希表:用于记录当前窗口内每种灯的数量;
- 哈希表(Hash Table)是一种常用的数据结构,用于存储键值对(key-value pairs)。它通过哈希函数将键映射到一个索引位置,从而实现快速的插入、删除和查找操作。哈希表的主要优点是平均时间复杂度为 O(1),即在理想情况下,操作的时间复杂度是常数级别的。
滑动窗口:用于动态调整窗口的大小,用于找到包含所有三种灯的最短子串。
- 滑动窗口(Sliding Window)是一种常用的算法技巧,用于解决数组或字符串中的子数组或子串问题。滑动窗口的核心思想是通过两个指针(通常称为
left和right)来动态调整窗口的大小,从而在数组或字符串中找到满足特定条件的子数组或子串。
算法的步骤
-
初始化:
- 使用一个哈希表
count来记录当前窗口内每种灯的数量。 - 初始化两个指针
left和right,分别表示窗口的左右边界。 - 初始化
min_length为N,表示当前找到的最短子串长度。
- 使用一个哈希表
-
扩展窗口:
- 移动
right指针,扩展窗口,并更新哈希表中对应灯的数量。
- 移动
-
缩小窗口:
- 当窗口内包含所有三种灯时(即
count['R'] > 0、count['G'] > 0、count['B'] > 0),尝试缩小窗口。 - 移动
left指针,缩小窗口,并更新哈希表中对应灯的数量。 - 在每次缩小窗口时,更新
min_length。
- 当窗口内包含所有三种灯时(即
-
返回结果:
- 如果
min_length没有被更新,说明没有找到符合条件的子串,返回-1。 - 否则,返回
min_length。
下面是给出的伪代码
- 如果
function solution(N, S):
// 初始化哈希表
count = { 'R': 0, 'G': 0, 'B': 0 }
left = 0
right = 0
min_length = N
while right < N:
// 扩展窗口
count[S[right]]++
right++
// 当窗口内包含所有三种灯时,尝试缩小窗口
while count['R'] > 0 and count['G'] > 0 and count['B'] > 0:
// 更新最小长度
min_length = min(min_length, right - left)
// 缩小窗口
count[S[left]]--
left++
// 如果 min_length 没有被更新,说明没有找到符合条件的子串
return min_length == N ? -1 : min_length
解释
- 哈希表
count:用于记录当前窗口内每种灯的数量。 - 滑动窗口:通过
left和right指针动态调整窗口大小,以找到包含所有三种灯的最短子串。 min_length:记录当前找到的最短子串长度,初始化为N,表示最长的子串长度。
总结
通过使用哈希表和滑动窗口的结合,我们可以高效地找到包含所有三种灯的最短子串。滑动窗口的动态调整和哈希表的状态记录使得算法能够在 O(n) 的时间复杂度内解决问题。