滑动窗口思想

今天刷随想录,接下来就开始介绍数组操作中另一个重要的方法:滑动窗口

滑动窗口算法简介

滑动窗口算法是一种通过定义窗口在数据结构上的滑动,以解决问题的方法。通常,窗口由两个指针表示,一个用于维护窗口的起始位置,另一个用于维护窗口的结束位置。算法的核心思想是在遍历过程中,通过移动这两个指针,调整窗口的大小和位置,以满足特定的条件。

算法步骤

  1. 初始化指针: 设立两个指针,通常表示窗口的起始位置(start)和结束位置(end)。

  2. 遍历数组: 从数组的第一个元素开始,进行遍历。

  3. 窗口调整: 在遍历过程中,根据问题的具体条件,通过移动指针调整窗口的大小和位置。

  4. 更新最优解: 在每一步调整中,更新记录当前问题的最优解。

  5. 返回结果: 遍历完成后,返回记录的最优解。

案例应用:果树农场水果收集

考虑一个实际问题:在一排果树上收集水果,每个篮子只能装同一类型的水果。我们希望找到一种策略,使得能够收集到的水果数量最大。

具体步骤
  1. 初始化: 设立两个指针start和end,初始位置都为数组的第一个元素。

  2. 遍历果树数组: 在遍历的过程中,使用一个字典或数组来记录窗口内每种水果的数量。

  3. 窗口调整: 如果窗口内水果种类的数量大于2,移动start指针,缩小窗口,直到水果种类数量等于2。

  4. 更新最大窗口: 在每一步调整中,更新记录的最大窗口大小。

  5. 返回结果: 遍历完成后,最大窗口的大小即为能够收集到的最大水果数量。

代码实现

#include 
#include 
#include 

using namespace std;

int maxFruits(vector& fruits) {
    int start = 0, end = 0;
    unordered_map fruitCount;
    int maxWindowSize = 0;

    while (end < fruits.size()) {
        // 更新窗口
        fruitCount[fruits[end]]++;

        // 窗口调整
        while (fruitCount.size() > 2) {
            fruitCount[fruits[start]]--;
            if (fruitCount[fruits[start]] == 0) {
                fruitCount.erase(fruits[start]);
            }
            start++;
        }

        // 更新最大窗口
        maxWindowSize = max(maxWindowSize, end - start + 1);

        // 移动窗口
        end++;
    }

    return maxWindowSize;
}

int main() {
    // 示例用法
    vector fruits = {1, 2, 1, 2, 3};
    int result = maxFruits(fruits);

    cout << "最大水果收集量为: " << result << endl;

    return 0;
}

你可能感兴趣的:(算法,数据结构,leetcode)