归并排序

来源:互联网 发布:淘宝联盟订单查询 编辑:程序博客网 时间:2024/06/04 10:30

归并排序是一种高效的排序算法,时间复杂度为nlogn,与快排相当,是分治法的一种典型应用。

归并排序的思想是将若干个有序的序列合并为一个有序序列,常用的是二路归并,也就是将两个有序子序列合并为一个序列。

归并排序可用递归完成,第一次排序将序列分成两部分,第二次排序将两序列在分成两部分,如此下去,直到每个子序列只有一个元素,则子序列自然有序,然后合并即可。

归并操作的工作原理如下:

  1.申请空间,使其大小为两个已经排序序列之和,该空间用来存放合并后的序列

  2.设定两个指针,最初位置分别为两个已经排序序列的起始位置

  3.比较两个指针所指向的元素,选择相对小的元素放入到合并空间,并移动指针到下一位置

  4.重复步骤3直到某一指针达到序列尾

  5.将另一序列剩下的所有元素直接复制到合并序列尾

c++模板实现代码如下:

[cpp] view plaincopy
  1. <span style="font-size:18px;">#include <iostream>  
  2. #include <ctime>  
  3. using namespace std;  
  4.   
  5. //合并两个有序数组  
  6. template <typename T>  
  7. void mergerarray(T a[], int first, int mid, int last, T temp[])  
  8. {  
  9.     int i = first, j = mid+1;  
  10.     int m = mid, n = last;  
  11.     int k = 0;  
  12.     while (i <= m && j <= n){  
  13.         if (a[i] < a[j])  
  14.             temp[k++] = a[i++];  
  15.         else  
  16.             temp[k++] = a[j++];  
  17.     }  
  18.     while (i <= m)  
  19.         temp[k++] = a[i++];  
  20.     while (j <= n)  
  21.         temp[k++] = a[j++];  
  22.     for (i=0; i<k; ++i)  
  23.         a[first+i] = temp[i];  
  24. }  
  25.   
  26. template <typename T>  
  27. void mergersort(T a[], int first, int last, T temp[])  
  28. {  
  29.     if (first < last){  
  30.         int mid = (first+last)/2;  
  31.         mergersort(a, first, mid, temp);  
  32.         mergersort(a, mid+1, last, temp);  
  33.         mergerarray(a, first, mid, last, temp);  
  34.     }  
  35. }  
  36.   
  37. template <typename T>  
  38. void MergerSort(T a[], int n)  
  39. {  
  40.     int* p = new int[n];  
  41.     if (p == NULL)  
  42.         return ;  
  43.     mergersort(a, 0, n-1, p);  
  44. }  
  45.   
  46. template <typename T>  
  47. void show(T a[], int n)  
  48. {  
  49.     for(int i=0; i<n; ++i)  
  50.         cout << a[i] << ' ';  
  51.     cout << endl;  
  52. }</span>  


测试代码如下:

[cpp] view plaincopy
  1. <span style="font-size:18px;">int main()  
  2. {  
  3.     const int N = 100000;  
  4.     int a[N];  
  5.   
  6.     for (int i=0; i<N; ++i)  
  7.         a[i] = N-i;  
  8.   
  9.     clock_t t1 = clock();//记录排序开始时间  
  10.     MergerSort(a, N);  
  11.     clock_t t2 = clock();//记录排序结束时间  
  12.   
  13.     //测试对100000个数的排序时间  
  14.     cout << "sort time: " << (double)(t2-t1)/CLOCKS_PER_SEC << "s" << endl;  
  15.   
  16.     return 0;  
  17. }</span>