归并排序

  (二路)归并排序的基本思想:将顺序表中的每个记录看成一个有序的子序列,然后两两归并有序的子序列,如此重复,直到得到一个包含所有记录的有序表。

  以顺序表L = {0,9,1,5,8,3}为例,length = 5,r[0]不参与排序。

  递归实现代码如下所示:

  由于我们是通过递归来实现归并排序的,所以外封了一个函数merge_sort()。

 1 //将arr[start,...mid]和arr[mid+1,...,end]归并到arr[start,...,end],reg[]为中间变量
 2 void Merge(int arr[], int reg[], int start, int mid, int end)
 3 {
 4     int start1 = start, end1 = mid;//待归并数组的前半部分arr[start,...mid]
 5     int start2 = mid + 1, end2 = end;//待归并数组的后半部分arr[mid+1,...,end]
 6     int k = start;
 7 
 8     while (start1 <= end1 && start2 <= end2)//将arr中的记录由小到大归并到reg中
 9         reg[k++] = arr[start1] < arr[start2] ? arr[start1++] : arr[start2++];
10     while (start1 <= end1)//将剩余元素复制到reg中
11         reg[k++] = arr[start1++];
12     while (start2 <= end2)//将剩余元素复制到reg中
13         reg[k++] = arr[start2++];
14     for (k = start; k <= end; k++)//将reg中的元素复制到arr中
15         arr[k] = reg[k];
16 }
 1 //将arr[start, ..., end]归并为有序的arr[start, ..., end]
 2 //int arr[],待排序的数组,int reg[], 中间变量
 3 //int start, int end,待排序数组的起始位置
 4 void merge_sort_recursive(int arr[], int reg[], int start, int end)
 5 {
 6     if (start == end)
 7         return;
 8 
 9     int mid = (start + end) / 2;
10 
11     merge_sort_recursive(arr, reg, start, mid);//将arr[start, ..., mid]归并为有序的arr[start, ..., mid]
12     merge_sort_recursive(arr, reg, mid + 1, end);//将arr[mid+1, ..., end]归并为有序的arr[mid+1, ..., end]
13 
14     //将arr[start,...mid]和arr[mid+1,...,end]归并到reg[start,...,end]
15     //再将reg[start,...,end]的值赋值给arr[start,...,end]
16     Merge(arr, reg, start, mid, end);
17 }
1 //int arr[], int len,待排序数组和待排序数组的长度
2 void merge_sort(int arr[], int len) 
3 {
4     //int reg[len];//定义数组的尺寸时不能用变量
5     int *reg=new int[len];//用作中间变量
6     merge_sort_recursive(arr, reg, 1, len);
7 }

  顺序表中的记录变化如下所示:

 

 

  如上图所示,为归并排序的详细步骤,在调用归并排序代码的过程中,步骤(1)-(13)依次执行,其中,红绿蓝三色的字中,归并时各个参数的值来源于前面步骤中相同颜色的部分,如步骤(6)中start,mid和end的值与步骤(4)和(5)中的对应值相同,(4)和(5)属于同一层次的递归。

 

相关链接:

冒泡排序 https://www.cnblogs.com/yongjin-hou/p/13858510.html

简单选择排序 https://www.cnblogs.com/yongjin-hou/p/13859148.html
直接插入排序 https://www.cnblogs.com/yongjin-hou/p/13861458.html
希尔排序 https://www.cnblogs.com/yongjin-hou/p/13866344.html

堆排序 https://www.cnblogs.com/yongjin-hou/p/13873770.html

快速排序 https://www.cnblogs.com/yongjin-hou/p/13950379.html

 

参考书籍:程杰 著,《大话数据结构》,清华大学出版社。

posted @ 2020-11-03 16:45  封狼居胥!  阅读(114)  评论(0编辑  收藏  举报