标签:
http://acm.hdu.edu.cn/showproblem.php?pid=5775
for(int i=1;i<=N;++i)
for(int j=N,t;j>i;—j)
if(P[j-1] > P[j])
t=P[j],P[j]=P[j-1],P[j-1]=t;
1 #include <cstring> 2 #include <cstdio> 3 #include <algorithm> 4 #include <iostream> 5 #include <cmath> 6 using namespace std; 7 #define N 100005 8 /* 9 树状数组 10 从右边往左扫看右边有多少个数是小于当前位置的数的, 11 然后可以达到的最右距离就是最初始的位置加上小于它的数的数量 12 可以达到的最左距离是min(最初始的位置,i) 13 所以最右减去最左就是i的答案了. 14 */ 15 int bit[N]; 16 int num[N], tmp[N], r[N]; 17 18 int lowbit(int x) 19 { 20 return x & (-x); 21 } 22 23 void update(int x) 24 { 25 while(x <= N) { 26 bit[x] += 1; 27 x += lowbit(x); 28 } 29 } 30 31 int query(int x) 32 { 33 int ans = 0; 34 while(x) { 35 ans += bit[x]; 36 x -= lowbit(x); 37 } 38 return ans; 39 } 40 41 int main() 42 { 43 int t; 44 scanf("%d", &t); 45 for(int cas = 1; cas <= t; cas++) { 46 memset(bit, 0, sizeof(bit)); 47 int n; 48 scanf("%d", &n); 49 for(int i = 1; i <= n; i++){ 50 scanf("%d", num+i); 51 tmp[num[i]] = i; 52 } 53 for(int i = n; i > 0; i--) { 54 update(num[i]); 55 r[num[i]] = query(num[i] - 1); 56 } 57 58 printf("Case #%d: ", cas); 59 for(int i = 1; i <= n; i++) { 60 if(i != n) printf("%d ", abs(tmp[i]+r[i] - min(tmp[i], i))); 61 else printf("%d\n", abs(tmp[i]+r[i] - min(tmp[i], i))); 62 } 63 } 64 return 0; 65 }
标签:
原文地址:http://www.cnblogs.com/fightfordream/p/5719743.html