BZOJ4385 [POI2015]Wilcze doły

Keywords: PHP

Tag: monotonous queue

subject

Topic portal

Description

Given a sequence of length n, you have a chance to select a continuous interval of length no more than d and change all the numbers to zero.

Please find the longest continuous interval so that the sum of all the numbers in the interval does not exceed p.

Input

The first line contains three integers n,p,d(1 < d < n < 2000000, 0 < p < 1016)n,p,d(1 < d < n < 2000000, 0 < p < 1016).

The second line contains n positive integers, representing i n turn each number w[i](1 < w[i] < 109)w[i](1 < w[i] < 109) i n the sequence.

Output

Contains a line of positive integers, that is, the length of the longest qualified interval that can be found after modification.

Sample Input

9 7 2
3 4 1 9 4 1 7 1 3

Sample Output

5

HINT

The fourth and fifth numbers are changed to 0, and then the intervals [2,6] [2,6] can be selected. The total number is 4+1+0+0+1=64+1+0+0+1=6.

Analysis

"Some players are not good at the level, so they can only save the choice to brush water."

The conclusion of greedy nature: the number d must be deleted

Then the monotonous queue sweeps over

code

#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cmath>
#include<cstring>
#include<algorithm>
#define rep(i,a,b) for(int i=a;i<=b;i++)
#define dep(i,a,b) for(int i=a;i>=b;i--)
#define ll long long
#define mem(x,num) memset(x,num,sizeof x)
#define reg(x) for(int i=last[x];i;i=e[i].next)
using namespace std;
inline ll read(){
    ll f=1,x=0;char ch=getchar();
    while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
    while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=getchar();}
    return x*f;
}
//**********head by yjjr**********
const int maxn=2e6+6;
int n,d,a[maxn];ll s[maxn],f[maxn],que[maxn<<2],p;
int main()
{
    n=read(),p=read(),d=read();
    rep(i,1,n)a[i]=read(),s[i]=s[i-1]+a[i];
    rep(i,0,n)f[i]=s[min(n,i+d)]-s[i];
    int head=1,tail=1,now=0,ans=d;que[1]=0;
    rep(i,d+1,n){
        while(head<=tail&&f[que[tail]]<f[i-d])tail--;
        que[++tail]=i-d;
        while(now<i-d&&s[now]+f[que[head]]<s[i]-p){
            now++;
            if(now>que[head])head++;
        }
        ans=max(ans,i-now);
    }
    cout<<ans<<endl;
    return 0;
}

Posted by RockinPurdy on Wed, 06 Feb 2019 09:45:16 -0800