数据结构——单调栈&单调队列(解决滑动窗口问题)

单调队列解答:

/*******************单调队列!=优先队列单调队列是为了保证队列内的元素具有单调性,在保持了元素原本顺序的同时,对元素进行了过滤,舍弃了会影响单调性的元素而优先队列本质上还是个队列不会舍弃任何元素,每个元素都在队列之中,但是在队列中的位置由优先队列定义的优先级来确定,损失了原数组中的数据相对位置关系。所以很显然,单调队列是解决:寻找在某元素左侧区间或者右侧区间的最值问题,而优先队列的应用是寻找整个区间内的最高优先级别的内容。/*******************#include<iostream>
using namespace std;

const int N = 1000010;

int n, m ,hh , tt;
int a[N];
int q[N];

int main(){
    scanf("%d%d",&n,&m);

    for(int i = 0 ; i < n ; i ++) scanf("%d",&a[i]);
    hh = 0;tt = -1;
    //单调递增序列
    for(int i = 0 ; i < n ; i ++){
        //滑动窗口内数据调整
        if( hh<=tt && q[hh] < i+1-m ) hh++;
        while( hh <= tt && a[q[tt]] >= a[i] ){ tt--; }
        q[ ++tt ] = i;
        if( i >= m - 1 ) printf("%d ",a[q[hh]]);
    }
    puts("");

    hh = 0;tt = -1;
    //单调递减序列
    for(int i = 0 ; i < n ;i ++){
        //调整滑动窗口内的数据
        if(hh <= tt && q[hh] < i+1-m){hh++;}
        while(hh <= tt && a[q[tt]] <= a[i] ) tt--;
        q[++tt] = i;
        if(i >= m-1) printf("%d ",a[q[hh]]);
    }
    puts("");
    return 0;
}

//单调栈,类似单调队列,对不满足单调性的数据进行筛选确保栈内元素单调
#include<iostream>
using namespace std;
const int N = 100010;
int n,m;
int st[N],tt;

int main(){
    cin>>n;
    int x;
    for(int i = 0 ; i < n ;i ++){
        cin>>x;
        while( tt > 0 && st[tt]>=x ) tt--;
        if(tt==0){cout<<-1<<" ";}
        else{
            cout<<st[tt]<<" ";
        }
        st[++tt] = x;
    }

    return 0;
}

原文地址:https://www.cnblogs.com/Flydoggie/p/12259072.html

时间: 2024-10-06 17:56:35

数据结构——单调栈&单调队列(解决滑动窗口问题)的相关文章

剑指Offer(栈和队列)-滑动窗口的最大值

(滑动窗口的最大值)题目描述: 给定一个数组和滑动窗口的大小,找出所有滑动窗口里数值的最大值.例如,如果输入数组{2,3,4,2,6,2,5,1}及滑动窗口的大小3,那么一共存在6个滑动窗口,他们的最大值分别为{4,4,6,6,6,5}: 针对数组{2,3,4,2,6,2,5,1}的滑动窗口有以下6个: {[2,3,4],2,6,2,5,1}, {2,[3,4,2],6,2,5,1}, {2,3,[4,2,6],2,5,1}, {2,3,4,[2,6,2],5,1}, {2,3,4,2,[6,2

单调队列(滑动窗口问题)

Description An array of size n ≤ 106 is given to you. There is a sliding window of size k which is moving from the very left of the array to the very right. You can only see the k numbers in the window. Each time the sliding window moves rightwards b

单调栈 、 队列学习

推荐博客 :https://blog.csdn.net/zuzhiang/article/details/78134247 单调栈.队列只需满足两个条件即可,序列是单调的,并且符合栈和队列的特性. 实现: 例如实现一个单调递增的栈,比如现在有一组数10,3,7,4,12.从左到右依次入栈,则如果栈为空或入栈元素值小于栈顶元素值,则入栈:否则,如果入栈则会破坏栈的单调性,则需要把比入栈元素小的元素全部出栈.单调递减的栈反之. 10入栈时,栈为空,直接入栈,栈内元素为10. 3入栈时,栈顶元素10比

【数据结构】栈和队列

栈和队列 容器数据结构是指一些包含了若干个其他相同或不同的数据结构的数据结构,被包含的这些每一个独立的数据结构都被称为一个元素,在一个容器中的元素往往支持相同的操作,具有类似的性质.之前说到过的线性表其实就是一种容器数据结构,本文中介绍的两种最常用的容器数据结构是栈和队列. 从功能上看,栈和队列大多用于计算过程中保存临时数据,这些数据是在计算过程中发现或产生的.在而后的计算中可能会用到这些数据.如果这些数据是固定的个数以及大小的话,可以构建几个变量来储存它们,但是如果这些数据不确定的话,就需要一

二、数据结构之栈、队列、循环队列

二.数据结构之栈.队列.循环队列 顺序栈 Stack.h 结构类型,函数声明: #ifndef _STACK_H_ #define _STACK_H_ typedef int SElementType; ///顺序栈 #define STACK_INIT_SIZE 20 #define STACK_INCREMENT 10 typedef struct { SElementType * base; SElementType * top; int stackSize;///当前栈的大小 }SqSt

详解--单调队列 经典滑动窗口问题

单调队列,即单调的队列.使用频率不高,但在有些程序中会有非同寻常的作用. 动态规划·单调队列的理解 做动态规划时常常会见到形如这样的转移方程: f[x] = max or min{g(k) | b[x] <= k < x} + w[x] (其中b[x]随x单调不降,即b[1]<=b[2]<=b[3]<=...<=b[n]) (g[k]表示一个和k或f[k]有关的函数,w[x]表示一个和x有关的函数) 这个方程怎样求解呢?我们注意到这样一个性质:如果存在两个数j, k,使

【单调队列】--滑动窗口

题目链接 给定一个大小为n≤106n≤106的数组. 有一个大小为k的滑动窗口,它从数组的最左边移动到最右边. 您只能在窗口中看到k个数字. 每次滑动窗口向右移动一个位置. 以下是一个例子: 该数组为[1 3 -1 -3 5 3 6 7],k为3. 窗口位置 最小值 最大值 [1 3 -1] -3 5 3 6 7 -1 3 1 [3 -1 -3] 5 3 6 7 -3 3 1 3 [-1 -3 5] 3 6 7 -3 5 1 3 -1 [-3 5 3] 6 7 -3 5 1 3 -1 -3 [5

数据结构之单调栈单调队列模板

单调栈 int rear=0; for(int st=1;st<=N;st++) { while(rear>0&&H[que[rear]]>=H[st]) --rear; if(rear==0) le[st]=0; else le[st]=que[rear]; que[++rear]=st; } 单调队列 int que[maxn],elem[maxn]; int front=1,rear=0; for(int i=1;i<K;i++) { while(rear&g

7.14 单调栈 单调队列 +dp优化

单调栈和单调队列的定义具体看ppt了 模板: 单调队列 head =1; tail = 0; rep( i ,1 ,n ){ while( head <= tail && a[i] < dq[tail].first)tail--; while( head <= tail && dq[head].second < i-k+1) head++; dq[ ++tail ]={a[i] ,i}; 例题:https://vjudge.net/contest/3