计算二维前缀和,更新一下归并的板子
#include<bits/stdc++.h> using namespace std; typedef long long ll; const int N=5e5+10; struct node{ int x,y,z,p,id,sign; ll sum; bool operator <(const node & t)const{ if(x!=t.x) return x<t.x; if(y!=t.y) return y<t.y; return z<t.z; } }q[N],w[N]; int cnt=0; ll ans[N]; void cdq(int l,int r){ if (l >= r) return; int mid=l+r>> 1; cdq(l, mid); cdq(mid + 1, r); int i=l, j=mid+1,k = 0; ll sum=0; while(i<=mid&&j<=r) if(q[i].y<=q[j].y) sum+=!q[i].z*q[i].p,w[k++]=q[i ++ ]; else q[j].sum+=sum, w[k ++ ] = q[j ++ ]; while (i<=mid) sum+=!q[i].z*q[i].p,w[k++]=q[i ++ ]; while (j<=r) q[j].sum+=sum,w[k ++ ]=q[j ++ ]; for(i=l,j=0; j<k;i++,j++) q[i]=w[j]; } int main(){ ios::sync_with_stdio(false); int n,m; cin>>n>>m; int i,j; for(i=1;i<=n;i++){ int a,b,c; cin>>a>>b>>c; q[++cnt]={a,b,0,c}; } for(i=1;i<=m;i++){ int x1,y1,x2,y2; cin>>x1>>y1>>x2>>y2; q[++cnt]={x1-1,y1-1,1,0,i,1}; q[++cnt]={x2,y2,1,0,i,1}; q[++cnt]={x1-1,y2,1,0,i,-1}; q[++cnt]={x2,y1-1,1,0,i,-1}; } sort(q+1,q+1+cnt); cdq(1,cnt); for(i=1;i<=cnt;i++){ if(q[i].z){ ans[q[i].id]+=q[i].sum*q[i].sign; } } for(i=1;i<=m;i++){ cout<<ans[i]<<endl; } }