在nlgn时间内实现逆序对数的计算

数组中逆序对的数量是同运行插入排序产生的移动的数量是相同的,但是选择排序的最差的时间复杂度是n的平方次,但是合并排序最差的是nlogn的时间复杂度。所以应该修改合并排序来计算逆序对数量。在L和R合并的过程中,如果没有移动的话,序列是L+R,所以计算移动的数量就是元素没有移动过R与L与R合并后的位置之间的差值就是移动的数量。

以下代码是实现的算法:

  1. #include<iostream>
  2. constintMAXINT=0xFFFF-1;
  3. voidInversionMerge(intA[],intstart,intmid,intend,int&c)
  4. {
  5. intlen1=mid-start+1+1;//加一个位置用于保存哨兵
  6. intlen2=end-mid+1;//加一个位置用于保存哨兵
  7. int*L=newint[len1];
  8. int*R=newint[len2];
  9. for(inti=0;i<len1-1;i++)
  10. L[i]=A[start+i];
  11. L[len1-1]=MAXINT;
  12. for(intj=0;j<len2-1;j++)
  13. R[j]=A[mid+j+1];
  14. R[len2-1]=MAXINT;
  15. i=0;j=0;
  16. for(intk=start;k<=end;k++)
  17. {
  18. if(L[i]<=R[j])
  19. {
  20. A[k]=L[i];
  21. i++;
  22. }
  23. else
  24. {
  25. A[k]=R[j];
  26. c=c+((mid+1+j)-k);
  27. j++;
  28. }
  29. }
  30. }
  31. voidInversionMergeSort(intA[],intstart,intend,int&c)
  32. {
  33. if(start<end)
  34. {
  35. intmid=(end+start)/2;
  36. InversionMergeSort(A,start,mid,c);
  37. InversionMergeSort(A,mid+1,end,c);
  38. InversionMerge(A,start,mid,end,c);
  39. }
  40. }
  41. intmain(void)
  42. {
  43. int*a;
  44. intc=0;//保存逆序对数量
  45. intn;
  46. std::cout<<"Pleaseinputthearray'ssize:/n";
  47. std::cin>>n;
  48. a=newint[n];
  49. std::cout<<"Pleaseinputthearray'value:"<<std::endl;
  50. for(inti=0;i<n;i++)
  51. std::cin>>a[i];
  52. InversionMergeSort(a,0,n-1,c);
  53. std::cout<<"Thesortednumberseries:";
  54. for(i=0;i<n;i++)
  55. std::cout<<""<<a[i];
  56. std::cout<<std::endl;
  57. std::cout<<"theInversionNumberIs"<<c<<std::endl;
  58. return0;
  59. }

答案经检验是正确的,开心!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值