题目
题解
cdq分治+树状数组,这里贴的是2683的代码,1176还要改一下
#include<bits/stdc++.h>
using namespace std;
const int M=800002,N=500002;
struct node{
int fl,x,y,v,pos,id;
}a[M],b[M];
int ans[N],s,cnt,tot,i,x,y,xx,yy,n,tr[N],opt,v;
inline char gc(){
static char buf[100000],*p1=buf,*p2=buf;
return p1==p2&&(p2=(p1=buf)+fread(buf,1,100000,stdin),p1==p2)?EOF:*p1++;
}
#define gc getchar
inline int read(){
int x=0,fl=1;char ch=gc();
for (;ch<48||ch>57;ch=gc())if(ch=='-')fl=-1;
for (;48<=ch&&ch<=57;ch=gc())x=(x<<3)+(x<<1)+(ch^48);
return x*fl;
}
inline void wri(int a){if(a<0)a=-a,putchar('-');if(a>=10)wri(a/10);putchar(a%10|48);}
inline void wln(int a){wri(a);puts("");}
void add(int x,int y){
for (;x<=n;x+=x&-x) tr[x]+=y;
}
int query(int x){
int s=0;
for (;x;x^=x&-x) s+=tr[x];
return s;
}
void solve(int l,int r){
if (l>=r) return;
int mid=l+r>>1,k1=l,k2=mid+1;
for (int i=l;i<=r;i++){
if (!a[i].fl && a[i].pos<=mid) add(a[i].y,a[i].v);
if (a[i].fl && a[i].pos>mid) ans[a[i].id]+=query(a[i].y)*a[i].v;
}
for (int i=l;i<=r;i++)
if (!a[i].fl && a[i].pos<=mid) add(a[i].y,-a[i].v);
for (int i=l;i<=r;i++)
if (a[i].pos<=mid) b[k1++]=a[i];
else b[k2++]=a[i];
for (int i=l;i<=r;i++) a[i]=b[i];
solve(l,mid);solve(mid+1,r);
}
bool cmp(node a,node b){
return a.x<b.x || a.x==b.x && a.pos<b.pos;
}
int main(){
n=read();
while (1){
opt=read();if (opt==3) break;
x=read();y=read();
if (opt==1){
v=read();
a[++cnt]=(node){0,x,y,v,cnt,0};
}else{
xx=read();yy=read();tot++;
a[++cnt]=(node){1,xx,yy,1,cnt,tot};
a[++cnt]=(node){1,xx,y-1,-1,cnt,tot};
a[++cnt]=(node){1,x-1,yy,-1,cnt,tot};
a[++cnt]=(node){1,x-1,y-1,1,cnt,tot};
}
}
sort(a+1,a+cnt+1,cmp);
solve(1,cnt);
for (i=1;i<=tot;i++) wln(ans[i]);
}