萌新求助,10分,全T
查看原帖
萌新求助,10分,全T
121027
Spasmodic楼主2020/11/22 23:50

怀疑写死循环了,因为bzoj上1000的点都T了

#include<bits/stdc++.h>
using namespace std;
struct IO_Tp {
    const static int _I_Buffer_Size = 2 << 22;
    char _I_Buffer[_I_Buffer_Size], *_I_pos = _I_Buffer;

    const static int _O_Buffer_Size = 2 << 22;
    char _O_Buffer[_O_Buffer_Size], *_O_pos = _O_Buffer;

    IO_Tp() { fread(_I_Buffer, 1, _I_Buffer_Size, stdin); }
    ~IO_Tp() { fwrite(_O_Buffer, 1, _O_pos - _O_Buffer, stdout); }

    IO_Tp &operator>>(int &res) {
    	int f=1;
        while (!isdigit(*_I_pos)&&(*_I_pos)!='-') ++_I_pos;
        if(*_I_pos=='-')f=-1,++_I_pos;
        res = *_I_pos++ - '0';
        while (isdigit(*_I_pos)) res = res * 10 + (*_I_pos++ - '0');
        res*=f;
        return *this;
    }

    IO_Tp &operator<<(int n) {
    	if(n<0)*_O_pos++='-',n=-n;
        static char _buf[10];
        char *_pos = _buf;
        do
            *_pos++ = '0' + n % 10;
        while (n /= 10);
        while (_pos != _buf) *_O_pos++ = *--_pos;
        return *this;
    }

    IO_Tp &operator<<(char ch) {
        *_O_pos++ = ch;
        return *this;
    }
} IO;

const int N=2000005,INF=2147483647;
int n,m,a[N];
//FHQ
int cnt,ch[N][2],v[N],pri[N],sz[N];
void pushup(int x){sz[x]=sz[ch[x][0]]+sz[ch[x][1]]+1;}
void split(int nw,int k,int&x,int&y){
	if(!nw)return x=y=0,void();
	else if(v[nw]<=k)x=nw,split(ch[nw][1],k,ch[nw][1],y);
	else y=nw,split(ch[nw][0],k,x,ch[nw][0]);
	pushup(nw);
}
int merge(int A,int B){
	if(!A||!B)return A+B;
	if(pri[A]<pri[B])return ch[A][1]=merge(ch[A][1],B),pushup(A),A;
	else return ch[B][0]=merge(A,ch[B][0]),pushup(B),B;
}
int x,y,z;
int newnode(int a){
	sz[++cnt]=1,v[cnt]=a,pri[cnt]=rand();
	return cnt;
}
void ins(int &rt,int a){
	split(rt,a,x,y);
	rt=merge(merge(x,newnode(a)),y);
}
void del(int &rt,int a){
	split(rt,a,x,z),split(x,a-1,x,y);
	y=merge(ch[y][0],ch[y][1]);
	rt=merge(merge(x,y),z);
}
int rk(int &rt,int a){
	split(rt,a-1,x,y);
	int ret=sz[x];
	rt=merge(x,y);
	return ret;
}
int pre(int &rt,int a){
	split(rt,a-1,x,y);
	int k=x;
	if(!k)return -INF;
	while(ch[x][1])x=ch[x][1];
	int ret=v[x];
	rt=merge(x,y);
	return ret;
}
int succ(int &rt,int a){
	split(rt,a,x,y);
	int k=y;
	if(!k)return INF;
	while(ch[y][0])x=ch[y][0];
	int ret=v[y];
	rt=merge(x,y);
	return ret;
}
//seg
int rt[N<<2];
void build(int k,int l,int r){
	if(l==r){
		rt[k]=newnode(a[l]);
		return;
	}
	for(int i=l;i<=r;i++)ins(rt[k],a[i]);
	int mid=l+r>>1;
	build(k<<1,l,mid);
	build(k<<1|1,mid+1,r);
}
void change(int k,int l,int r,int p,int v){
	if(l>p||r<p)return;
	del(rt[k],a[p]);
	ins(rt[k],v);
	if(l==r)return;
	int mid=l+r>>1;
	change(k<<1,l,mid,p,v);
	change(k<<1|1,mid+1,r,p,v); 
}
int qrk(int k,int l,int r,int x,int y,int v){
	if(x>r||y<l)return 0;
	if(x<=l&&r<=y)return rk(rt[k],v);
	int mid=l+r>>1,ret=0;
	ret+=qrk(k<<1,l,mid,x,y,v);
	ret+=qrk(k<<1|1,mid+1,r,x,y,v);
	return ret;
}
int qkth(int x,int y,int K){
	int l=0,r=1e8,ans=0;
	while(l<=r){
		int mid=l+r>>1;
		if(qrk(1,1,n,x,y,mid)+1<=K)ans=mid,l=mid+1;
		else r=mid-1;
	}
	return ans;
}
int qpre(int k,int l,int r,int x,int y,int v){
	if(x>r||y<l)return -INF;
	if(x<=l&&r<=y)return pre(rt[k],v);
	int mid=l+r>>1,ret=-INF;
	ret=max(ret,qpre(k<<1,l,mid,x,y,v));
	ret=max(ret,qpre(k<<1|1,mid+1,r,x,y,v));
	return ret;
}
int qsucc(int k,int l,int r,int x,int y,int v){
	if(x>r||y<l)return INF;
	if(x<=l&&r<=y)return succ(rt[k],v);
	int mid=l+r>>1,ret=INF;
	ret=min(ret,qsucc(k<<1,l,mid,x,y,v));
	ret=min(ret,qsucc(k<<1|1,mid+1,r,x,y,v));
	return ret;
}
int main(){
	IO>>n>>m;
	for(int i=1;i<=n;i++)IO>>a[i];
	build(1,1,n); 
	while(m--){
		int op,l,r,pos,k;
		IO>>op;
		if(op==1)IO>>l>>r>>k,IO<<qrk(1,1,n,l,r,k)+1<<'\n';
		else if(op==2)IO>>l>>r>>k,IO<<qkth(l,r,k)<<'\n';
		else if(op==3)IO>>pos>>k,change(1,1,n,pos,k),a[pos]=k;
		else if(op==4)IO>>l>>r>>k,IO<<qpre(1,1,n,l,r,k)<<'\n';
		else IO>>l>>r>>k,IO<<qsucc(1,1,n,l,r,k)<<'\n';
	}
	return 0;
}
2020/11/22 23:50
加载中...