TiCl4 @ 2019-07-20 22:48:27
我的
数组开到
#include<bits/stdc++.h>
using namespace std;
typedef int ll;
const ll MAXN=2e6+51;
const double alpha=0.75;
ll dim;
struct Node{
ll val;
ll d[2];
inline bool operator <(const Node &rhs)const;
};
struct KDTree{
Node nd;
ll sum,size;
ll minn[2],maxn[2],ch[2];
inline void clear()
{
minn[0]=minn[1]=maxn[0]=maxn[1]=sum=size=nd.d[0]=nd.d[1]=nd.val=0;
}
};
Node nd[MAXN];
KDTree tree[MAXN];
ll cnt,ptr,ptr2,tot,x,y,xx,yy,z,op,lastAns,rt;
ll pool[MAXN];
inline ll read()
{
register ll num=0,neg=1;
register char ch=getchar();
while(!isdigit(ch)&&ch!='-')
{
ch=getchar();
}
if(ch=='-')
{
neg=-1;
ch=getchar();
}
while(isdigit(ch))
{
num=(num<<3)+(num<<1)+(ch-'0');
ch=getchar();
}
return num*neg;
}
inline void chkmin(ll &x,ll y)
{
if(x>y)
{
x=y;
}
}
inline void chkmax(ll &x,ll y)
{
if(x<y)
{
x=y;
}
}
inline bool Node::operator <(const Node &rhs)const
{
return this->d[dim]<rhs.d[dim];
}
inline ll newNode()
{
if(!ptr)
{
return ++tot;
}
tree[pool[ptr]].clear();
return pool[ptr--];
}
inline void update(ll x,ll y)
{
chkmin(tree[x].minn[0],tree[y].minn[0]);
chkmin(tree[x].minn[1],tree[y].minn[1]);
chkmax(tree[x].maxn[0],tree[y].maxn[0]);
chkmax(tree[x].maxn[1],tree[y].maxn[1]);
}
inline void update(ll node)
{
ll ls=tree[node].ch[0],rs=tree[node].ch[1];
tree[node].minn[0]=tree[node].maxn[0]=tree[node].nd.d[0];
tree[node].minn[1]=tree[node].maxn[1]=tree[node].nd.d[1];
tree[node].size=tree[ls].size+tree[rs].size+1;
tree[node].sum=tree[ls].sum+tree[rs].sum+tree[node].nd.val;
if(ls)
{
update(node,ls);
}
if(rs)
{
update(node,rs);
}
}
inline ll create(ll l,ll r,ll d)
{
ll mid=(l+r)>>1;
dim=d,nth_element(nd+l,nd+mid,nd+r);
ll node=newNode();
tree[node].nd=nd[mid];
tree[node].ch[0]=l<mid?create(l,mid-1,d^1):0;
tree[node].ch[1]=r>mid?create(mid+1,r,d^1):0;
update(node);
return node;
}
inline void pia(ll node)
{
if(tree[node].ch[0])
{
pia(tree[node].ch[0]);
}
nd[++ptr2]=tree[node].nd;
pool[++ptr]=node;
if(tree[node].ch[1])
{
pia(tree[node].ch[1]);
}
}
inline void check(ll &node,ll d)
{
ll ls=tree[node].ch[0],rs=tree[node].ch[1];
double sz=alpha*tree[node].size;
if(sz<tree[ls].size||sz<tree[rs].size)
{
ptr2=0,pia(node),node=create(1,ptr2,d);
}
}
inline void insert(Node nd,ll d,ll &node)
{
if(!node)
{
node=newNode(),tree[node].nd=nd,update(node);
return;
}
ll x=tree[node].nd.d[d]<nd.d[d];
insert(nd,d^1,tree[node].ch[x]);
update(node),check(node,d);
}
inline ll check(KDTree nd,ll x,ll y,ll xx,ll yy)
{
ll p=nd.minn[0],q=nd.minn[1],r=nd.maxn[0],s=nd.maxn[1];
if(x<=p&&xx>=r&&y<=q&&yy>=s)
{
return 1;
}
if((xx<p||x>r)||(yy<q||y>s))
{
return 0;
}
return 2;
}
inline ll query(ll x,ll y,ll xx,ll yy,ll node)
{
ll chk,res=0,p=tree[node].nd.d[0],q=tree[node].nd.d[1];
ll ls=tree[node].ch[0],rs=tree[node].ch[1];
if(p>=x&&p<=xx&&q>=y&&q<=yy)
{
res+=tree[node].nd.val;
}
if(ls)
{
chk=check(tree[ls],x,y,xx,yy);
if(chk==1)
{
res+=tree[ls].sum;
}
if(chk==2)
{
res+=query(ls,x,y,xx,yy);
}
}
if(rs)
{
chk=check(tree[rs],x,y,xx,yy);
if(chk==1)
{
res+=tree[rs].sum;
}
if(chk==2)
{
res+=query(rs,x,y,xx,yy);
}
}
return res;
}
int main()
{
cnt=read();
while(1)
{
op=read();
if(op==3)
{
return 0;
}
if(op==1)
{
x=read()^lastAns,y=read()^lastAns,z=read()^lastAns;
insert((Node){z,x,y},0,rt);
}
else
{
x=read()^lastAns,y=read()^lastAns;
xx=read()^lastAns,yy=read()^lastAns;
printf("%d\n",lastAns=query(x,y,xx,yy,rt));
}
}
}