• luoguP1886 滑动窗口


    发一波树状数组的版本

    单调队列是最快的

    树状数组也可以过

    需要吸氧这里使用了手动O3

    具体怎么写就是树状数组的板子题,单点修改区间查询最值,注意初始值的设置调了很久

    #pragma GCC optimize(3)
    #include<cstring>
    #include<iostream>
    #include<algorithm>
    using namespace std;
    const int N=1000005;
    int n,k,a[N],c[N],b[N];
    inline int lowbit(int x){return (x&(-x));}
    inline void modify1(int pos,int val)
    {for(;pos<=n;pos+=lowbit(pos))c[pos]=max(c[pos],val);}
    inline void modify2(int pos,int val)
    {for(;pos<=n;pos+=lowbit(pos))b[pos]=min(b[pos],val);}
    inline int query1(int l,int r)
    {
        int ans=-0x7fffffff;
        while(r>=l)
        {
            ans=max(ans,a[r]);
            for(r--;r-lowbit(r)>=l;r-=lowbit(r))
            ans=max(ans,c[r]);
        }
        return ans;
    }
    inline int query2(int l,int r)
    {
        int ans=0x7fffffff;
        while(r>=l)
        {
            ans=min(ans,a[r]);
            for(r--;r-lowbit(r)>=l;r-=lowbit(r))
            ans=min(ans,b[r]);
        }
        return ans;
    }
    int main()
    {
        ios::sync_with_stdio(false);
        cin>>n>>k;
        memset(c,-0x3f,sizeof(c));
        memset(b,0x3f,sizeof(b));
        for(int i=1;i<=n;i++)cin>>a[i],modify1(i,a[i]),modify2(i,a[i]);
        for(int i=k;i<=n;i++)cout<<query2(i-k+1,i)<<" ";
        cout<<endl;
        for(int i=k;i<=n;i++)cout<<query1(i-k+1,i)<<" ";
    }
    

    再发一下单调队列的,不用吸氧
    版本一STL

    #include<iostream>
    #include<deque>
    using namespace std;
    const int N=1000005;
    int n,k;
    struct node{int v,id;}a[N];
    deque<node> qmin,qmax;
    int main()
    {
        cin>>n>>k;
        for(int i=1;i<=n;i++)cin>>a[i].v,a[i].id=i;
        for(int i=1;i<=n;i++)
        {
            while(!qmin.empty()&&qmin.back().v>=a[i].v)qmin.pop_back();
            qmin.push_back(a[i]);
            if(qmin.front().id==i-k)qmin.pop_front();
            if(i>=k)cout<<qmin.front().v<<" ";
        }
        cout<<endl;
        for(int i=1;i<=n;i++)
        {
            while(!qmax.empty()&&qmax.back().v<=a[i].v)qmax.pop_back();
            qmax.push_back(a[i]);
            if(qmax.front().id==i-k)qmax.pop_front();
            if(i>=k)cout<<qmax.front().v<<" ";
        }
    }
    

    版本二数组模拟

    #include"iostream"
    using namespace std;
    const int N=1000005;
    int n,k,a[N],h,t;
    struct deque{int v,id;}qmax[N],qmin[N];
    int main()
    {
        cin>>n>>k;
        for(int i=1;i<=n;i++)cin>>a[i];	
        h=t=1;
        for(int i=1;i<=n;i++)
        {
            while(h!=t&&qmin[t-1].v>=a[i])t--;
            qmin[t].v=a[i],qmin[t++].id=i;
            if(qmin[h].id==i-k)h++;
            if(i>=k)cout<<qmin[h].v<<" ";
        }
        cout<<endl; 
        h=t=1;
        for(int i=1;i<=n;i++)
        {
            while(h!=t&&qmax[t-1].v<=a[i])t--;
            qmax[t].v=a[i],qmax[t++].id=i;
            if(qmax[h].id==i-k)h++;
            if(i>=k)cout<<qmax[h].v<<" ";
        }
    }
    

    主要是想推广一下树状数组,这个数据结构非常好,会比线段树快,还十分好写

  • 相关阅读:
    WPF 文本滚动效果 渐变效果
    Unity3D 学习——入门资料整理
    命名管道 问题:信号灯超时问题
    Nginx 遇到的问题
    Nginx的安装配置 例子
    03 Spring的父子容器
    02 浅析Spring的AOP(面向切面编程)
    03 JVM的垃圾回收机制
    02 Java类的加载机制
    01 深入理解JVM的内存区域
  • 原文地址:https://www.cnblogs.com/Ace-MYX/p/10617347.html
Copyright © 2020-2023  润新知