TLE+WA 0 分,不指望有人帮忙调代码,能给组hack数据么
code:
#include<cmath>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
int n,m;
int sq,q[200005],lzy[200005];
struct node
{
int num,id;
}a[200005];//存排序后的数组
node pp[6005],qq[6005];
bool cmp(node x,node y){return x.num<y.num;}
inline int read()//快读
{
int x=0;int f=1;char c=getchar();
while(c<'0'||c>'9'){if(c=='-')f=-1;c=getchar();}
while(c>='0'&&c<='9'){x=(x<<3)+(x<<1)+(c^48);c=getchar();}
return x*f;
}
inline void write(int x)//快输
{
if(x<0){x=~(x-1);putchar('-');}
if(x>9) write(x/10);
putchar(x%10+'0');
return ;
}
void change(int l,int r,int k)
{
int lp=0,lq=0;
for(int i=q[l-1]*sq+1;i<=q[l]*sq;i++)//记录全新的值
if(a[i].id<l||a[i].id>r) pp[++lp]=a[i];
else a[i].num+=k,qq[++lq]=a[i];
int pi=1,qi=1,t=q[l-1]*sq+1;
while(t<=q[l]*sq)//合并
{
if(pi<=lp&&(qi>lq||pp[pi].num<qq[qi].num)) a[t++]=pp[pi],pi++;
else a[t++]=qq[qi],qi++;
}
//左碎块
if(q[l]!=q[r])
{
lp=0,lq=0;
for(int i=q[r-1]*sq+1;i<=q[r]*sq;i++)
if(a[i].id<l||a[i].id>r) pp[++lp]=a[i];
else a[i].num+=k,qq[++lq]=a[i];
pi=1,qi=1,t=q[l-1]*sq+1;
while(t<=q[r]*sq)
{
if(pi<=lp&&(qi>lq||pp[pi].num<qq[qi].num)) a[t++]=pp[pi],pi++;
else a[t++]=qq[qi],qi++;
}
}
//右碎块
for(int i=q[l]+1;i<q[r];i++) lzy[i]+=k;//整块
return ;
}
int query(int l,int r,int k)
{
int res=0;
for(int i=q[l-1]*sq+1;i<=q[l]*sq;i++)
if(a[i].id>=l&&a[i].id<=r&&a[i].num+lzy[q[l]]<=k) res++;
//左碎快
if(q[l]!=q[r])
for(int i=q[r-1]*sq+1;i<=q[r]*sq;i++)
if(a[i].id>=l&&a[i].id<=r&&a[i].num+lzy[q[r]]<=k) res++;
//右碎块
for(int i=q[l]+1;i<q[r];i++)
{
int le=(i-1)*sq+1,ri=i*sq;
while(le<ri)
{
int mid=(le+ri)/2+1;
if(a[mid].num+lzy[i]<=k) le=mid;
else ri=mid-1;
}
res+=le-(i-1)*sq;
}
return res;
}
int main()
{
n=read(),m=read();
if(n==1) sq=sqrt(n);
else sq=sqrt(n)*(int)floor(log2(n));
for(int i=1;i<=n;i++)
{
a[i].num=read();
q[i]=(i-1)/sq+1;
a[i].id=i;
}
for(int i=1;i<=n;)
{
int j;
for(j=i;q[j]==q[i];j++);
sort(a+i,a+j,cmp);
i=j;
}
for(int i=1;i<=m;i++)
{
int opt=read(),l=read(),r=read(),k=read();
if(opt==1)
{
if(r-l+1<k) printf("-1\n");
else
{
int le=2e9,ri=-2e9;
for(int i=q[l-1]*sq+1;i<=q[l]*sq;i++)
if(a[i].id>=l&&a[i].id<=r)
{
if(le>a[i].num+lzy[q[l]])
le=a[i].num+lzy[q[l]];
if(ri<a[i].num+lzy[q[l]])
ri=a[i].num+lzy[q[l]];
}
if(q[l]!=q[r])
for(int i=q[r-1]*sq+1;i<=q[r]*sq;i++)
if(a[i].id>=l&&a[i].id<=r)
{
if(le>a[i].num+lzy[q[r]])
le=a[i].num+lzy[q[r]];
if(ri<a[i].num+lzy[q[r]])
ri=a[i].num+lzy[q[r]];
}
for(int i=q[l]+1;i<q[r];i++)
{
if(le>a[(i-1)*sq+1].num+lzy[i])
le=a[(i-1)*sq+1].num+lzy[i];
if(ri<a[i*sq].num+lzy[i])
ri=a[i*sq].num+lzy[i];
}
while(le<ri)
{
int mid=(le+ri)/2;
if(query(l,r,mid)<k) le=mid+1;
else ri=mid;
}
write(ri);
puts("");
}
}
else change(l,r,k);
}
return 0;
}