[整體二分 樹狀陣列套線段樹] BZOJ 2674 Attack
阿新 • • 發佈:2019-02-16
大暴力啊 96s+卡過
//本地明明44s+
//要了資料才知道相對頂點可以不是左下和右上
#include<cstdio> #include<cstdlib> #include<algorithm> using namespace std; inline char nc(){ static char buf[100000],*p1=buf,*p2=buf; if (p1==p2) { p2=(p1=buf)+fread(buf,1,100000,stdin); if (p1==p2) return EOF; } return *p1++; } inline void read(int &x){ char c=nc(),b=1; for (;!(c>='0' && c<='9');c=nc()) if (c=='-') b=-1; for (x=0;c>='0' && c<='9';x=x*10+c-'0',c=nc()); x*=b; } inline void read(char &x){ for (x=nc();x!='S' && x!='Q';x=nc()); } const int N=60005,ND=5000005; int sx[N],sy[N],sp[N]; int icnt; inline int Bin1(int *a,int x){ return lower_bound(a+1,a+a[0]+1,x)-a; } inline int Bin2(int *a,int x){ return upper_bound(a+1,a+a[0]+1,x)-a-1; } int Stk[ND],pnt; inline void Init(){ for (int i=ND-1;i;i--) Stk[++pnt]=i; } inline int New(){ return Stk[pnt--]; } inline void Del(int x) { Stk[++pnt]=x; } int ls[ND],rs[ND],sum[ND]; void Add(int &x,int l,int r,int t,int s){ if (!x) x=New(); int mid=(l+r)>>1; if (l==r) { sum[x]+=s; if (!sum[x]) Del(x),x=0; return; } if (t<=mid) Add(ls[x],l,mid,t,s); else Add(rs[x],mid+1,r,t,s); sum[x]=sum[ls[x]]+sum[rs[x]]; if (!sum[x]) Del(x),x=0; } int Query(int x,int l,int r,int L,int R){ if (!x) return 0; int mid=(l+r)>>1; if (L<=l && r<=R) return sum[x]; if (R<=mid) return Query(ls[x],l,mid,L,R); else if (L>mid) return Query(rs[x],mid+1,r,L,R); else return Query(ls[x],l,mid,L,mid)+Query(rs[x],mid+1,r,mid+1,R); } namespace BIT{ #define lowbit(x) ((x)&-(x)) int maxn; int c[N]; inline void init(int n){ maxn=n; } inline void add(int x,int y,int r){ for (int i=x;i<=maxn;i+=lowbit(i)) Add(c[i],1,icnt,y,r); } inline int sum(int x,int L,int R){ int ret=0; for (int i=x;i;i-=lowbit(i)) ret+=Query(c[i],1,icnt,L,R); return ret; } } int n,m; const int E=100005; struct event{ int f,x1,y1,x2,y2,p,k,idx; event(){ } event(int f,int x1,int y1,int x2,int y2,int p,int k,int idx):f(f),x1(x1),x2(x2),y1(y1),y2(y2),k(k),p(p),idx(idx) {} }eve[E],tmpl[E],tmpr[E]; int tot,il,ir; int _x[N],_y[N],_p[N]; int ans[N],qq; inline void Solve(int l,int r,int L,int R) { if (l>r) return; if (L==R){ for (int i=l;i<=r;i++) if (eve[i].f) ans[eve[i].idx]=L; return; } int mid=(L+R)>>1,tem; il=ir=0; for (int i=l;i<=r;i++) if (!eve[i].f){ if (eve[i].p<=mid) BIT::add(eve[i].x1,eve[i].y1,eve[i].k),tmpl[++il]=eve[i]; else tmpr[++ir]=eve[i]; }else{ tem=BIT::sum(eve[i].x2,eve[i].y1,eve[i].y2)-BIT::sum(eve[i].x1-1,eve[i].y1,eve[i].y2); if (tem<eve[i].k) eve[i].k-=tem,tmpr[++ir]=eve[i]; else tmpl[++il]=eve[i]; } for (int i=r;i>=l;i--) if (!eve[i].f && eve[i].p<=mid) BIT::add(eve[i].x1,eve[i].y1,-eve[i].k); int top=l-1,mi; for (int i=1;i<=il;i++) eve[++top]=tmpl[i]; mi=top; for (int i=1;i<=ir;i++) eve[++top]=tmpr[i]; Solve(l,mi,L,mid); Solve(mi+1,r,mid+1,R); } int main() { char order; int u,v,x1,x2,y1,y2,k; freopen("t.in","r",stdin); freopen("t.out","w",stdout); Init(); read(n); read(m); for (int i=1;i<=n;i++) { read(_x[i]),read(_y[i]),read(_p[i]); sx[++sx[0]]=_x[i],sy[++sy[0]]=_y[i],sp[++sp[0]]=_p[i]; } sort(sx+1,sx+sx[0]+1); sx[0]=unique(sx+1,sx+sx[0]+1)-sx-1; sort(sy+1,sy+sy[0]+1); sy[0]=unique(sy+1,sy+sy[0]+1)-sy-1; sort(sp+1,sp+sp[0]+1); sp[0]=unique(sp+1,sp+sp[0]+1)-sp-1; for (int i=1;i<=n;i++) { _x[i]=Bin1(sx,_x[i]); _y[i]=Bin1(sy,_y[i]); _p[i]=Bin1(sp,_p[i]); eve[++tot]=event(0,_x[i],_y[i],0,0,_p[i],1,0); } for (int i=1;i<=m;i++) { read(order); if (order=='S') { read(u); read(v); u++; v++; if (u==v) continue; eve[++tot]=event(0,_x[u],_y[u],0,0,_p[u],-1,0); eve[++tot]=event(0,_x[u],_y[u],0,0,_p[v],1,0); eve[++tot]=event(0,_x[v],_y[v],0,0,_p[v],-1,0); eve[++tot]=event(0,_x[v],_y[v],0,0,_p[u],1,0); swap(_p[u],_p[v]); } else { read(x1); read(y1); read(x2); read(y2); read(k); if (x1>x2) swap(x1,x2); if (y1>y2) swap(y1,y2); x1=Bin1(sx,x1); x2=Bin2(sx,x2); y1=Bin1(sy,y1); y2=Bin2(sy,y2); if (x1>x2 || y1>y2) ans[++qq]=sp[0]+1; else eve[++tot]=event(1,x1,y1,x2,y2,0,k,++qq); } } icnt=sy[0]; BIT::init(sx[0]); Solve(1,tot,1,sp[0]+1); for (int i=1;i<=qq;i++) if (ans[i]==sp[0]+1) printf("It doesn't exist.\n"); else printf("%d\n",sp[ans[i]]); return 0; }