Ultra-QuickSort
Time Limit: 7000MS | Memory Limit: 65536K | |
Total Submissions: 39782 | Accepted: 14340 |
Description
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 ,
Ultra-QuickSort 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.
Ultra-QuickSort produces the output
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
题意:
给出数 n (0 ~ 500000)代表有 n 个数,后给出这 n 个数(0 ~ 999999999),求出需要交换的次数使这个序列变为递增序列。
思路:
树状数组 + 离散化。离散化用 排序 + map 会导致 TLE,所以要用 排序 + 去重 + 二分 来离散化,结果应该要为 long long 型的。题目即为求逆序数,运用树状数组即可求出。
AC:
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
typedef long long ll;
const ll MAX = 500005;
ll num[MAX], s_num[MAX];
ll bit[MAX], n;
void add(ll i, ll x) {
while (i <= n) {
bit[i] += x;
i += i & -i;
}
}
ll sum(ll i) {
ll s = 0;
while (i > 0) {
s += bit[i];
i -= i & -i;
}
return s;
}
int main() {
while (~scanf("%I64d", &n) && n) {
for (ll i = 0; i < n; ++i) {
scanf("%I64d", &num[i]);
s_num[i] = num[i];
bit[i + 1] = 0;
}
sort(s_num, s_num + n);
ll ans = 0;
for (ll i = 0; i < n; ++i) {
int in = lower_bound(s_num, s_num + n, num[i]) - s_num;
ans += i - sum(in);
add(in + 1, 1);
}
printf("%I64d\n", ans);
}
return 0;
}