题解:
CDQ分治什么不存在的。
直接找不相交的,然后分八种情况维护一下即可。
#include <bits/stdc++.h>
using namespace std;
const int RLEN=1<<18|1;
inline char nc() {
static char ibuf[RLEN],*ib,*ob;
(ib==ob) && (ob=(ib=ibuf)+fread(ibuf,1,RLEN,stdin));
return (ib==ob) ? -1 : *ib++;
}
inline int rd() {
char ch=nc(); int i=0,f=1;
while(!isdigit(ch)) {if(ch=='-')f=-1; ch=nc();}
while(isdigit(ch)) {i=(i<<1)+(i<<3)+ch-'0'; ch=nc();}
return i*f;
}
const int N=1e5+50;
int n,tot,id[N];
int totx,toty;
struct matrix {
int l,r,u,d,v;
} mat[N];
struct ST_1D {
int rt,tot,lc[N*60],rc[N*60],sze[N*60];
inline void add(int &k,int l,int r,int p,int v) {
if(!k) k=++tot; sze[k]+=v;
if(l==r) return;
int mid=(l+r)>>1;
(p<=mid) ? add(lc[k],l,mid,p,v) : add(rc[k],mid+1,r,p,v);
}
inline int ask(int k,int l,int r,int L,int R) {
if(l>r) return 0;
if(!sze[k]) return 0;
if(L<=l && r<=R) return sze[k];
int mid=(l+r)>>1;
if(R<=mid) return ask(lc[k],l,mid,L,R);
else if(L>mid) return ask(rc[k],mid+1,r,L,R);
else return ask(lc[k],l,mid,L,R)+ask(rc[k],mid+1,r,L,R);
}
inline void add(int x,int v) {add(rt,1,max(totx,toty),x,v);}
inline int ask(int l,int r) {return ask(rt,1,max(totx,toty),l,r);}
} s1[4];
struct ST_2D {
int rt[N*2],lc[N*300],rc[N*300],sze[N*300],tot;
inline void add(int &k,int l,int r,int p,int v) {
if(!k) k=++tot; sze[k]+=v;
if(l==r) return;
int mid=(l+r)>>1;
(p<=mid) ? add(lc[k],l,mid,p,v) : add(rc[k],mid+1,r,p,v);
}
inline int ask(int k,int l,int r,int L,int R) {
if(!sze[k]) return 0;
if(L<=l && r<=R) return sze[k];
int mid=(l+r)>>1;
if(R<=mid) return ask(lc[k],l,mid,L,R);
else if(L>mid) return ask(rc[k],mid+1,r,L,R);
else return ask(lc[k],l,mid,L,R)+ask(rc[k],mid+1,r,L,R);
}
inline void add(int x,int y,int v) {
for(int i=x;i<=totx;i+=i&(-i)) add(rt[i],1,toty,y,v);
}
inline int ask(int lx,int rx,int ly,int ry) {
if(lx>rx || ly>ry) return 0;
int ans=0;
for(int i=rx;i;i-=i&(-i)) ans+=ask(rt[i],1,toty,ly,ry);
for(int i=lx-1;i;i-=i&(-i)) ans-=ask(rt[i],1,toty,ly,ry);
return ans;
}
} s2[4];
inline void init() {
n=rd();
vector <int> vl;
vector <int> vu;
for(int i=1;i<=n;i++) {
char ch=nc(); while(!isalpha(ch)) ch=nc();
if(ch=='I') {
id[++tot]=i;
mat[i].l=rd(), mat[i].d=rd();
mat[i].r=rd(), mat[i].u=rd();
mat[i].v=1;
vl.push_back(mat[i].l), vl.push_back(mat[i].r);
vu.push_back(mat[i].u), vu.push_back(mat[i].d);
} else if(ch=='Q') {
mat[i].l=rd(), mat[i].d=rd();
mat[i].r=rd(), mat[i].u=rd();
mat[i].v=0;
vl.push_back(mat[i].l), vl.push_back(mat[i].r);
vu.push_back(mat[i].u), vu.push_back(mat[i].d);
} else {
mat[i]=mat[id[rd()]];
mat[i].v=-1;
}
}
sort(vl.begin(),vl.end()); vl.erase(unique(vl.begin(),vl.end()),vl.end());
sort(vu.begin(),vu.end()); vu.erase(unique(vu.begin(),vu.end()),vu.end());
totx=vl.size(); toty=vu.size();
#define id(x,y) (lower_bound(x.begin(),x.end(),y)-x.begin()+1)
for(int i=1;i<=n;i++) {
mat[i].l=id(vl,mat[i].l);
mat[i].r=id(vl,mat[i].r);
mat[i].u=id(vu,mat[i].u);
mat[i].d=id(vu,mat[i].d);
}
}
int main() {
init(); int sum=0;
for(int i=1;i<=n;i++) {
if(mat[i].v) {
sum+=mat[i].v;
s1[0].add(mat[i].r,mat[i].v);
s1[1].add(mat[i].l,mat[i].v);
s1[2].add(mat[i].d,mat[i].v);
s1[3].add(mat[i].u,mat[i].v);
s2[0].add(mat[i].r,mat[i].d,mat[i].v);
s2[1].add(mat[i].r,mat[i].u,mat[i].v);
s2[2].add(mat[i].l,mat[i].d,mat[i].v);
s2[3].add(mat[i].l,mat[i].u,mat[i].v);
} else {
int ans=0;
ans+=s1[0].ask(1,mat[i].l-1);
ans+=s1[1].ask(mat[i].r+1,totx);
ans+=s1[2].ask(mat[i].u+1,toty);
ans+=s1[3].ask(1,mat[i].d-1);
ans-=s2[0].ask(1,mat[i].l-1,mat[i].u+1,toty);
ans-=s2[1].ask(1,mat[i].l-1,1,mat[i].d-1);
ans-=s2[2].ask(mat[i].r+1,totx,mat[i].u+1,toty);
ans-=s2[3].ask(mat[i].r+1,totx,1,mat[i].d-1);
printf("%d\n",sum-ans);
}
}
}