5618 Jam's problem again
阿新 • • 發佈:2019-02-04
題目:給你n個點(x,y,z),讓你輸出對於每個點(xi,yi,zi)滿足xj<=xi&&yj<=yi&&zj<=zi的點的數目
思路:先按照x排序,然後做分治的時候針對y排序,這樣會漏掉相等的點對其左邊的點的影響,做一下預處理即可
程式碼:
#pragma comment(linker, "/STACK:1024000000,1024000000") #include<iostream> #include<algorithm> #include<ctime> #include<cstdio> #include<cmath> #include<cstring> #include<string> #include<vector> #include<map> #include<set> #include<queue> #include<stack> #include<list> #include<numeric> using namespace std; #define LL long long #define ULL unsigned long long #define INF 0x3f3f3f3f #define mm(a,b) memset(a,b,sizeof(a)) #define PP puts("*********************"); template<class T> T f_abs(T a){ return a > 0 ? a : -a; } template<class T> T gcd(T a, T b){ return b ? gcd(b, a%b) : a; } template<class T> T lcm(T a,T b){return a/gcd(a,b)*b;} // 0x3f3f3f3f3f3f3f3f //0x3f3f3f3f const int maxn=1e5+50; struct Node{ int x,y,z,id; }q[maxn],tmp[maxn]; bool cmp1(Node a,Node b){ if(a.x!=b.x) return a.x<b.x; if(a.y!=b.y) return a.y<b.y; return a.z<b.z; } bool cmp2(Node a,Node b){ if(a.y!=b.y) return a.y<b.y; return a.id<b.id; } struct BIT{ int n,b[maxn]; void init(int _n){ n=_n; mm(b,0); } void add(int i,int val){ for(;i<=n;i+=i&(-i)) b[i]+=val; } int sum(int i){ int ret=0; for(;i>0;i-=i&(-i)) ret+=b[i]; return ret; } }bit; int ans[maxn]; int n; void cdq(int L,int R){ if(L>=R) return; int sz=0,mid=(L+R)>>1; for(int i=L;i<=mid;i++){ tmp[sz]=q[i]; tmp[sz++].id=0; } for(int i=mid+1;i<=R;i++) tmp[sz++]=q[i]; sort(tmp,tmp+sz,cmp2); for(int i=0;i<sz;i++){ if(tmp[i].id==0) bit.add(tmp[i].z,1); else ans[tmp[i].id]+=bit.sum(tmp[i].z); } for(int i=0;i<sz;i++) if(tmp[i].id==0) bit.add(tmp[i].z,-1); cdq(L,mid); cdq(mid+1,R); } int main(){ // freopen("D:\\input.txt","r",stdin); // freopen("D:\\output.txt","w",stdout); int T; scanf("%d",&T); while(T--){ scanf("%d",&n); mm(ans,0); int mx=1; for(int i=1;i<=n;i++){ scanf("%d%d%d",&q[i].x,&q[i].y,&q[i].z); q[i].id=i; mx=max(mx,q[i].z); } bit.init(mx); sort(q+1,q+n+1,cmp1); int cnt=0; for(int i=n-1;i>=1;i--){ if(q[i].x==q[i+1].x&&q[i].y==q[i+1].y&&q[i].z==q[i+1].z) cnt++; else cnt=0; ans[q[i].id]+=cnt; } cdq(1,n); for(int i=1;i<=n;i++) printf("%d\n",ans[i]); } return 0; }