Chinaunix首页 | 论坛 | 博客
  • 博客访问: 83583
  • 博文数量: 25
  • 博客积分: 10
  • 博客等级: 民兵
  • 技术积分: 100
  • 用 户 组: 普通用户
  • 注册时间: 2012-06-12 22:35
文章分类
文章存档

2017年(7)

2016年(1)

2015年(17)

我的朋友

分类: C/C++

2017-11-08 23:42:10

简介

归并排序分为递归方法和循环处理方法,不建议使用递归,递归对程序堆栈不有好。

实现思路

1、循环实现:
2、递归实现:
	分而治之 

时间复杂度

归并排序一般在外排序的时候使用,需要额外的空间 O(N)

代码


点击(此处)折叠或打开

  1. #include
  2. #include
  3. #include

  4. /* L = 左边起始位置, R = 右边起始位置, RightEnd = 右边终点位置*/
  5. void Merge( int A[], int TmpA[], int L, int R, int RightEnd )
  6. { /* 将有序的A[L]~A[R-1]和A[R]~A[RightEnd]归并成一个有序序列 */
  7.      int LeftEnd, NumElements, Tmp;
  8.      int i;
  9.       
  10.      LeftEnd = R - 1; /* 左边终点位置 */
  11.      Tmp = L; /* 有序序列的起始位置 */
  12.      NumElements = RightEnd - L + 1;
  13.       
  14.      while( L <= LeftEnd && R <= RightEnd ) {
  15.          if ( A[L] <= A[R] )
  16.              TmpA[Tmp++] = A[L++]; /* 将左边元素复制到TmpA */
  17.          else
  18.              TmpA[Tmp++] = A[R++]; /* 将右边元素复制到TmpA */
  19.      }
  20.  
  21.      while( L <= LeftEnd )
  22.          TmpA[Tmp++] = A[L++]; /* 直接复制左边剩下的 */
  23.      while( R <= RightEnd )
  24.          TmpA[Tmp++] = A[R++]; /* 直接复制右边剩下的 */
  25.           
  26.      for( i = 0; i < NumElements; i++, RightEnd -- )
  27.          A[RightEnd] = TmpA[RightEnd]; /* 将有序的TmpA[]复制回A[] */
  28. }

  29. void Msort( int A[], int TmpA[], int L, int RightEnd )
  30. { /* 核心递归排序函数 */
  31.      int Center;

  32.      printf("L=%d,RightEnd=%d\n", L, RightEnd);
  33.      if ( L < RightEnd ) {
  34.           Center = (L+RightEnd) / 2;
  35.          printf("L=%d,Center=%d\n", L, Center);
  36.           Msort( A, TmpA, L, Center ); /* 递归解决左边 */
  37.          printf("### L=%d,Center=%d,RightEnd=%d\n", L, Center, RightEnd);
  38.           Msort( A, TmpA, Center+1, RightEnd ); /* 递归解决右边 */
  39.          printf("*** L=%d,Center=%d,RightEnd=%d\n", L, Center, RightEnd);
  40.           Merge( A, TmpA, L, Center+1, RightEnd ); /* 合并两段有序序列 */
  41.          printf("~~~ L=%d,Center=%d,RightEnd=%d\n", L, Center, RightEnd);
  42.      }
  43. }

  44. void MergeSort( int A[], int N )
  45. { /* 归并排序 - 递归实现 */
  46.      int *TmpA;
  47.      TmpA = (int *)malloc(N*sizeof(int));
  48.       
  49.      if ( TmpA != NULL ) {
  50.           Msort( A, TmpA, 0, N-1 );
  51.           free( TmpA );
  52.      }
  53.      else printf( "空间不足" );
  54. }


  55. /* 归并排序 - 循环实现 */
  56. /* length = 当前有序子列的长度*/
  57. void Merge_pass( int A[], int TmpA[], int N, int length )
  58. { /* 两两归并相邻有序子列 */
  59.      int i, j, k;
  60.        
  61.      for ( i=0; i <= N-2*length; i += 2*length )
  62.          Merge( A, TmpA, i, i+length, i+2*length-1 );
  63.      for(k = 0; k < N; k++) {
  64.         printf("\r\nA[%d] = %d\r\n", k, A[k]);
  65.      }
  66.      printf("i = %d, length = %d\n", i, length);
  67.      if ( i+length < N ) /* 归并最后2个子列*/
  68.          Merge( A, TmpA, i, i+length, N-1);
  69.      else /* 最后只剩1个子列*/
  70.          for ( j = i; j < N; j++ ) {
  71.              printf("==========\n");
  72.              TmpA[j] = A[j];
  73.          }
  74. }
  75.  
  76. void Merge_Sort( int A[], int N )
  77. {
  78.      int length, i;
  79.      int *TmpA;
  80.       
  81.      length = 1; /* 初始化子序列长度*/
  82.      TmpA = malloc( N * sizeof( int ) );
  83.      if ( TmpA != NULL ) {
  84.           while( length < N ) {
  85.               Merge_pass( A, TmpA, N, length );
  86.               length *= 2;
  87.              for(i = 0; i< N; i++) {
  88.                 printf("A[%d] = %d\n", i, A[i]);
  89.                 printf("TmpA[%d] = %d\n", i , TmpA[i]);
  90.               }
  91.              printf("N = %d, length = %d\n", N, length);
  92.               Merge_pass( TmpA, A, N, length );
  93.               length *= 2;
  94.           }
  95.           free( TmpA );
  96.      }
  97.      else printf( "空间不足" );
  98. }

  99. int main()
  100. {
  101.     /* 归并排序 */
  102.      int A[15] = {2,3,4,12,5,89,100,32,45,11,65,78,34,109,9};
  103.      int N=15;
  104.      int i ,j;
  105.     
  106.      for(i = 0; i< N; i++) {
  107.         printf("A[%d] = %d\n", i, A[i]);
  108.      }

  109.      //MergeSort(A, N); /*递归实现*/
  110.      Merge_Sort(A, N); /*循环实现*/

  111.      for(i = 0; i< N; i++) {
  112.         printf("A[%d] = %d\n", i, A[i]);
  113.      }
  114.     
  115.     return 1;
  116. }
阅读(1798) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~