Ultra-QuickSort
Time Limit: 7000MS Memory Limit: 65536K
Total Submissions: 56754 Accepted: 20985Description
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.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
0Sample Output
6
0Source
Waterloo local 2005.02.05
这个什么就是求逆序对,题目那么多我也不知道在说什么,我英语渣
然后感觉用树状数组来求实际上好麻烦poi
还要先离散,然后两个sort,用归并应该会快一点吧
本来我不知道怎么做觉得挺神秘的,但说起来很简单,就是按大小把每个数加到自己的位置上,然后去统计,0~他自己之间有多少个数
然后,有些时候数比较大,我们就要离散什么的
大概就是这样,如果会了树状数组的单点修改 区间求和理解起来应该很轻松
然后是我的代码:
#include<iostream>
#include<cstdio>
#include<cstring>
#include<string>
#include<set>
#include<map>
#include<queue>
#include<algorithm>
#include<vector>
#include<cstdlib>
#include<cmath>
#include<ctime>
#include<stack>
#define INF 2100000000
#define ll long long
#define clr(x) memset(x,0,sizeof(x))
#define clrmax(x) memset(x,127,sizeof(x))
using namespace std;
inline int read()
{
char c;
int ret=0;
while(!(c>='0'&&c<='9'))
c=getchar();
while(c>='0'&&c<='9')
{
ret=(c-'0')+(ret<<1)+(ret<<3);
c=getchar();
}
return ret;
}
#define M 500005
#define lowbit(x) (x&(-x))
int tree[M],n;
struct node
{
int num,f,no;
}a[M];
#define no(x) a[x].no
#define num(x) a[x].num
#define f(x) a[x].f
bool com(node a,node b)
{
return a.num<b.num;
}
bool com2(node a,node b)
{
return a.no<b.no;
}
void add(int x)
{
for(int i=x;i<=n;i+=lowbit(i))
tree[i]++;
}
int get_min(int x)
{
int ret=0;
for(int i=x;i;i-=lowbit(i))
ret+=tree[i];
return ret;
}
int main()
{
freopen("in.txt","r",stdin);
while(~scanf("%d",&n))
{
if(n==0)return 0;
clr(tree);
clr(a);
for(int i=1;i<=n;i++)
{
num(i)=read();
no(i)=i;
}
sort(a+1,a+n+1,com);
int cnt;
f(1)=cnt=1;
for(int i=2;i<=n;i++)
{
if(num(i)!=num(i-1))cnt++;
f(i)=cnt;
}
sort(a+1,a+n+1,com2);
ll ans=0;
for(int i=1;i<=n;i++)
{
add(f(i));
ans+=i-get_min(f(i));
}
cout<<ans<<'\n';
}
}
大概就是这个样子,如果有什么问题,或错误,请在评论区提出,谢谢。