A - Ultra-QuickSort
In this problem, you have to analyze a particular sorting algorithm. The algorithm processes a sequence of n distinct integers by swapping two adjacent sequence elements until the sequence is sorted in ascending order. For the input sequence
9 1 0 5 4 ,
produces the output
0 1 4 5 9 .
Your task is to determine how many swap operations Ultra-QuickSort needs to perform in order to sort a given input sequence.
Input
The input contains several test cases. Every test case begins with a line that contains a single integer n < 500,000 -- the length of the input sequence. Each of the the following n lines contains a single integer 0 ≤ a[i] ≤ 999,999,999, the i-th input sequence element. Input is terminated by a sequence of length n = 0. This sequence must not be processed.
Output
For every input sequence, your program prints a single line containing an integer number op, the minimum number of swap operations necessary to sort the given input sequence.
Sample Input
5
9
1
0
5
4
3
1
2
3
0
Sample Output
6
0
利用树状数组计算逆序数即可,注意数据类型的取值范围。
#include <iostream>
#include <cstdio>
#include <algorithm>
#include <vector>
#include <cstring>
#include <queue>
typedef long long ll;
using namespace std;
const ll maxn = 5e5+19;
int n;
ll A[maxn], B[maxn], C[maxn];
void add(ll x, ll d){
while(x <= n){
C[x] += d; x += x&-x;
}
}
ll sum(ll x){
ll ret = 0;
while(x > 0){
ret += C[x]; x -= x&-x;
}
return ret;
}
int main(){
#ifdef TEST
freopen("test.txt", "r", stdin);
#endif // TEST
while(cin >> n){
if(n == 0)
break;
memset(A, 0, sizeof(A));
memset(B, 0, sizeof(B));
memset(C, 0, sizeof(C));
for(int i = 1; i <= n; i++){
scanf("%lld", &A[i]);
B[i] = A[i];
}
// 对A[]离散化。
sort(B+1, B+n+1);
unique(B+1, B+n+1);
for(int i = 1; i <= n; i++){
A[i] = lower_bound(B+1, B+n+1, A[i]) - B;
}
ll res = 0;
for(int i = 1; i <= n; i++){
add(A[i], 1);
res += i-sum(A[i]);
}
printf("%lld\n", res);
}
return 0;
}