归并排序求逆序对数:
和归并排序一样,划分和递归求解都好理解,关键在于合并,对于右边的j ,统计出左边比j 大 的元素个数 f(j),所有的f(j)家和就是我们要的逆序对数!
在归并排序中,我们将右边的元素向临时数组中加入的时候,左边还没加入得便是比j 大的元素! 既有m-p个
在加右边时,不断累加m-p即可!
以 POJ 1804 为例!
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
int a[5007],b[5007],n,sum,ks;
void sort(int x,int y){
if (x + 1 >= y)return;
int m = x + (y-x)/2;
sort(x,m); sort(m,y);
int p = x, q = m, i = x;
while (p < m || q < y){
if (q >= y || (p < m && a[p] <= a[q])) b[i++] = a[p++];
else b[i++] = a[q++], sum+=m-p;
}
for (int i = x; i < y; ++i) a[i] = b[i];
}
int main(){
int T;
scanf("%d",&T);
while(T--){
scanf("%d",&n);
for (int i = 0; i < n; ++i)scanf("%d",a+i);
sum = 0;
sort(0,n);
if (ks++)puts("");
printf("Scenario #%d:\n%d\n",ks,sum);
}
return 0;
}
Brainman Description Background Input The first line contains the number of scenarios. Output Start the output for every scenario with a line containing "Scenario #i:", where i is the number of the scenario starting at 1. Then print a single line containing the minimal number of swaps of adjacent numbers that are necessary to sort the given sequence. Terminate the output for the scenario with a blank line. Sample Input 44 2 8 0 310 0 1 2 3 4 5 6 7 8 96 -42 23 6 28 -100 655375 0 0 0 0 0 Sample Output Scenario #1:3Scenario #2:0Scenario #3:5Scenario #4:0 Source TUD Programming Contest 2003, Darmstadt, Germany |
Time Limit: 1000MS | | Memory Limit: 30000K |
Total Submissions: 9861 | | Accepted: 5227 |
[Submit] [Go Back] [Status] [Discuss]