序列的 逆序数 = 在只允许相邻两个元素交换的条件下,得到有序序列的交换次数
#include<iostream> #include<cstdio> #include<cstring> using namespace std; int a[500010],t[500010]; long long ans;//必须用双长整型 void merge_sort(int *A,int x,int y,int *T)//归并排序 { if(y-x>1)//直到一个序列只有2个元素,则该序列的逆序数等于相邻交换的次数 { int p=x,m=x+(y-x)/2,q=m,i=x; merge_sort(A,x,m,T); merge_sort(A,m,y,T); while(p<m||q<y)//用短路运算符 { if(p>=m||(q<y&&A[p]>=A[q])) { T[i++]=A[q++]; ans+=m-p;//逆序数=交换次数 } else {T[i++]=A[p++];} } for(i=x;i<y;i++) A[i]=T[i];//从辅助空间复制回A数组 } } int main() { int n,i; while(~scanf("%d",&n),n) { ans=0; for(i=0;i<n;i++) scanf("%d",&a[i]); merge_sort(a,0,n,t); printf("%lld\n",ans); } return 0; }