Description
Solution
其实,这道题目的本质就是求出一段区间的平均数大于等于k
操作的实质就是移多补少
那么,我们把每一个数减去k
做一个前缀和
然后维护一个单调栈
因为我们发现
如果一个sum[i]>sum[i+1] 那显然当右端点确定的时候
会选择sum[i]
所以用个单调栈搞一搞就好了
Code
#include <cstdio>
#include <cstring>
#include <algorithm>
#define fo(i,a,b) for(i=a;i<=b;i++)
#define fd(i,a,b) for(i=a;i>=b;i--)
using namespace std;
int n,m,i,l,x,a[1000005],q[1000005];
long long sum[1000005];
int read(){
int sum=0;
char c=getchar();
while (c<'0'||c>'9') c=getchar();
while (c>='0'&&c<='9'){
sum=sum*10+c-'0';
c=getchar();}
return sum;
}
int main(){
freopen("1.in","r",stdin);
freopen("1.out","w",stdout);
n=read(),m=read();
fo(i,1,n) a[i]=read();
while (m){
m--;
x=read();
q[0]=1;
fo(i,1,n) {
sum[i]=sum[i-1]+a[i]-x;
if (sum[i]<sum[q[q[0]]]) q[++q[0]]=i;
}
x=0;
fd(i,n,1){
while (q[0]&&sum[i]>=sum[q[q[0]]]) q[0]--;
x=max(x,i-q[q[0]+1]);
}
printf("%d ",x);
}
}