Poj--3067(树状数组,逆序数)
2014-09-08 20:20:04
思路:也是求逆序数,但这题需要注意的是只计算在中间的交叉点,所以要排序时要处理一下。。。另外吐槽下这坑爹的数据范围。
1 /************************************************************************* 2 > File Name: p3067.cpp 3 > Author: Nature 4 > Mail: 564374850@qq.com 5 > Created Time: Mon 08 Sep 2014 07:38:35 PM CST 6 ************************************************************************/ 7 8 #include <cstdio> 9 #include <cstring> 10 #include <cstdlib> 11 #include <cmath> 12 #include <vector> 13 #include <queue> 14 #include <iostream> 15 #include <algorithm> 16 using namespace std; 17 typedef long long ll; 18 const int INF = 1 << 29; 19 const int maxn = 1000010; 20 21 struct node{ 22 int w,e; 23 friend bool operator < (const node &a,const node &b){ 24 if(a.w == b.w) return a.e < b.e; 25 return a.w < b.w; 26 } 27 }no[maxn]; 28 29 int T,N,M,K,c[maxn]; 30 31 int Lowbit(int x){return x & (-x);} 32 void Update(int x,int d){while(x <= maxn){c[x] += d,x += Lowbit(x);}} 33 int Getsum(int x){int res = 0;while(x){res += c[x],x -= Lowbit(x);}return res;} 34 35 int main(){ 36 scanf("%d",&T); 37 for(int t = 1; t <= T; ++t){ 38 memset(c,0,sizeof(c)); 39 scanf("%d%d%d",&N,&M,&K); 40 for(int i = 1; i <= K; ++i) 41 scanf("%d%d",&no[i].e,&no[i].w); 42 sort(no + 1,no + K + 1); 43 ll ans = 0; 44 for(int i = 1; i <= K; ++i){ 45 ans += Getsum(N) - Getsum(no[i].e); 46 Update(no[i].e,1); 47 } 48 printf("Test case %d: %lld\n",t,ans); 49 } 50 return 0; 51 }