基准时间限制:1 秒 空间限制:131072 KB 分值: 0 难度:基础题
在一个排列中,如果一对数的前后位置与大小顺序相反,即前面的数大于后面的数,那么它们就称为一个逆序。一个排列中逆序的总数就称为这个排列的逆序数。
如2 4 3 1中,2 1,4 3,4 1,3 1是逆序,逆序数是4。给出一个整数序列,求该序列的逆序数。
Input
第1行:N,N为序列的长度(n <= 50000) 第2 - N + 1行:序列中的元素(0 <= A[i] <= 10^9)
Output
输出逆序数
Input示例
4 2 4 3 1
Output示例
4
相关问题
求逆序数,最先想到的就是归并了,归并过程中后一半数组的插入次数就是逆序总数
#include <stdio.h>
#include <string.h>
#define MAXN 50010
long long s[MAXN];
long long num[MAXN];
long long cnt;
//归并排序
void merge( int start , int mid , int end ) {
int i = start;
int j = mid + 1;
int k = start;
// printf( "111cnt=%d\n",cnt );
while( i<=mid && j<=end ) {
if( num[i]<=num[j] )
s[k++] = num[i++];
else {
cnt += j-k;
s[k++] = num[j++];
}
}
while( i<=mid ) {
s[k++] = num[i++];
}
while( j<=end ) {
s[k++] = num[j++];
}
for( i=start ; i<=end ; i++ )
num[i] = s[i];
}
//将数组一分为2
void mergeSort( int start , int end ) {
if( start>=end )
return;
// printf( "222cnt=%d\n",cnt );
int mid = ( start+end )/2;
mergeSort( start,mid );
mergeSort( mid+1,end );
merge( start,mid,end );
}
int main() {
// freopen( "input.txt","r",stdin );
int n;
while( ~scanf( "%d",&n ) ) {
memset( num,0,sizeof(num) );
for( int i=0 ; i<n ; i++ ) {
scanf( "%d",&num[i] );
}
cnt = 0;
mergeSort( 0,n-1 );
printf( "%lld\n",cnt );
}
}
扫描二维码关注公众号,回复:
2628352 查看本文章