Loj-10176-最大连续和

题目

题目链接

测试得分:  100

主要算法 :  单调队列优化DP

题干:

   单调队列优化DP板子

   

  题意分析错误,但是有部分分

/*
这个代码使用滚动数组优化的暴力,有局限性,只能处理长度为m区间的最大连续和,而并不是小于等于m的
#include<stdio.h> #include<stdlib.h> #define FORa(i,s,e) for(int i=s;i<=e;i++) #define FORs(i,s,e) for(int i=s;i>=e;i--) #define gc getchar()//pa==pb&&(pb=(pa=buf)+fread(buf,1,100000,stdin),stdin)?EOF:*pa++ #define File(name) freopen(name".in","r",stdin);freopen(name".out","w",stdout); using namespace std; char buf[100000],*pa,*pb; inline int read(); const int K=2*1e5,INF=2147483647; int a,n,k,ans=-INF,sum[K+1]; inline int max(int fa,int fb){return fa>fb?fa:fb;} int main() { File("1"); n=read(),k=read(); FORa(i,1,n) { a=read(); sum[i%(k+1)]=sum[(i-1)%(k+1)]+a; if(i>=k) ans=max(ans,sum[i%(k+1)]-sum[(i-k)%(k+1)]); } printf("%d",ans); return 0; } inline int read() { register char c(gc);register int f(1),x(0); while(c<'0'||c>'9') f=c=='-'?-1:1,c=gc; while(c>='0'&&c<='9') x=(x<<1)+(x<<3)+(c^48),c=gc; return x*f; } */

   

  单调队列优化动规

#include<stdio.h>
#include<stdlib.h>
#define FORa(i,s,e) for(int i=s;i<=e;i++)
#define FORs(i,s,e) for(int i=s;i>=e;i--)
#define File(name) freopen(name".in","r",stdin);freopen(name".out","w",stdout);
using namespace std;

const int N=2*1e5,INF=2147483647;
int n,k,s[N+7],q[N+7],head=1,tail=0,ans=-INF;

/*将合法元素塞入容量为m的单调队列中,
如果现在这个比当前队列中后面较为劣的元素要好,删除比它劣的元素 */
inline int max(int fa,int fb){return fa>fb?fa:fb;}
int main()
{
    scanf("%d%d",&n,&k);
    FORa(i,1,n) scanf("%d",&s[i]),s[i]+=s[i-1];
    FORa(i,1,n)
    {
        while(head<=tail&&s[q[tail]-1]>=s[i-1]) tail--;//如果现在这个比当前队列中后面较为劣的元素要好,删除比它劣的元素 
        q[++tail]=i;//插入该元素,原理是这个元素必须要选 
        while(head<=tail&&q[head]<i-k+1) head++;
        ans=max(ans,s[i]-s[q[head]-1]);
    }
    printf("%d",ans);
}

原文地址:https://www.cnblogs.com/SeanOcean/p/11359990.html