mirror of
https://github.com/youngyangyang04/leetcode-master.git
synced 2025-08-06 01:20:05 +08:00
3.7 KiB
3.7 KiB
滑动窗口最大值
本题是 代码随想录:滑动窗口最大值 的升级版。
在代码随想录:滑动窗口最大值 中详细讲解了如何求解 滑动窗口的最大值。
那么求滑动窗口的最小值原理也是一样的, 大家稍加思考,把优先级队列里的 大于 改成小于 就行了。
求最大值的优先级队列(从大到小)
while (!que.empty() && value > que.back()) {
求最小值的优先级队列(从小到大)
while (!que.empty() && value > que.back()) {
这样在滑动窗口里 最大值最小值都求出来了,遍历一遍找出 差值最大的就好。
至于输入,需要一波字符串处理,比较考察基本功。
CPP代码如下:
#include <iostream>
#include <sstream>
#include <vector>
#include <string>
#include <deque>
using namespace std;
class MyBigQueue { //单调队列(从大到小)
public:
deque<int> que; // 使用deque来实现单调队列
// 每次弹出的时候,比较当前要弹出的数值是否等于队列出口元素的数值,如果相等则弹出。
// 同时pop之前判断队列当前是否为空。
void pop(int value) {
if (!que.empty() && value == que.front()) {
que.pop_front();
}
}
// 如果push的数值大于入口元素的数值,那么就将队列后端的数值弹出,直到push的数值小于等于队列入口元素的数值为止。
// 这样就保持了队列里的数值是单调从大到小的了。
void push(int value) {
while (!que.empty() && value > que.back()) {
que.pop_back();
}
que.push_back(value);
}
// 查询当前队列里的最大值 直接返回队列前端也就是front就可以了。
int front() {
return que.front();
}
};
class MySmallQueue { //单调队列(从小到大)
public:
deque<int> que;
void pop(int value) {
if (!que.empty() && value == que.front()) {
que.pop_front();
}
}
// 和上面队列的区别是这里换成了小于,
void push(int value) {
while (!que.empty() && value < que.back()) {
que.pop_back();
}
que.push_back(value);
}
int front() {
return que.front();
}
};
int main() {
string input;
getline(cin, input);
vector<int> nums;
int k;
// 找到并截取nums的部分
int numsStart = input.find('[');
int numsEnd = input.find(']');
string numsStr = input.substr(numsStart + 1, numsEnd - numsStart - 1);
// cout << numsStr << endl;
// 用字符串流处理nums字符串,提取数字
stringstream ss(numsStr);
string temp;
while (getline(ss, temp, ',')) {
nums.push_back(stoi(temp));
}
// 找到并提取k的值
int kStart = input.find("k = ") + 4;
k = stoi(input.substr(kStart));
MyBigQueue queB; // 获取区间最大值
MySmallQueue queS; // 获取区间最小值
// vector<int> result;
for (int i = 0; i < k; i++) { // 先将前k的元素放进队列
queB.push(nums[i]);
queS.push(nums[i]);
}
int result = queB.front() - queS.front();
for (int i = k; i < nums.size(); i++) {
queB.pop(nums[i - k]); // 滑动窗口移除最前面元素
queB.push(nums[i]); // 滑动窗口前加入最后面的元素
queS.pop(nums[i - k]);
queS.push(nums[i]);
result = max (result, queB.front() - queS.front());
}
cout << result << endl;
}