一、基本运算:
两路合并排序:将两个有序序列合并成一个有序序列。
二、步骤:
①把待排序的序列分成长度为1的子序列(只包含一个记录的序列被认为是有序的)→得到n个长度为1的有序子序列;
②实施两两合并,合并相邻的两个子序列→得到大约n/2个长度为2的有序子序列;
③重复步骤②,直到合并成一个长度为n的有序序列为止。
三、注意:
当待排序序列个数为奇数时,最后一个长度为1的子序列则在最后一趟进行排序。
四、举例:
以对序列A[0], A[l]…, A[n-1]进行升序排列来进行讲解,在此采用自顶向下的实现方法,操作步骤如下。
①将所要进行的排序序列分为左右两个部分,如果要进行排序的序列的起始元素下标为first,最后一个元素的下标为last,那么左右两部分之间的临界点下标mid=(first+last)/2,这两部分分别是A[first … mid]和A[mid+1 … last];
②将上面所分得的两部分序列继续按照步骤(1)继续进行划分,直到划分的区间长度为1;
③将划分结束后的序列进行归并排序,排序方法为对所分的n个子序列进行两两合并,得到n/2或n/2+l个含有两个元素的子序列,再对得到的子序列进行合并,直至得到一个长度为n的有序序列为止。
五、函数:
Merge函数
①功能:将两个有序序列合并成一个有序序列;
②C代码:
void Merge(int arr[],int low,int mid,int high)
{
int left_low=low; //左边序列的左下标
int left_high=mid;
int right_low=mid+1; //右边序列的左下标
int right_high=high;
int tmp[N],k=0,i; //数组tmp用来存放序列元素
while(left_low<=left_high&&right_low<=right_high) //当左右序列都有元素时执行循环
{
if(arr[left_low]<arr[right_low])
tmp[k++]=arr[left_low++]; //元素小的放进数组tmp
else
tmp[k++]=arr[right_low++];
}
if(left_low<=left_high){ //左边序列还有元素时
for(i=left_low;i<=left_high;i++)
tmp[k++]=arr[left_low++];
}
if(right_low<=right_high){ //右边序列还有元素时
for(i=right_low;i<=right_high;i++)
tmp[k++]=arr[right_low++];
}
for(i=0;i<high-low+1;i++){ //将数组tmp中的元素赋给数组arr,从而数组arr有序
arr[low+i]=tmp[i];
}
}
MergeSort函数
①功能:通过调用自身分裂子序列;通过调用Merge函数实现两路合并排序。
②代码:
void MergeSort(int arr[],int first,int last)
{
int mid = 0;
if(first<last){
mid = (first+last)/2; /* 注意防止溢出 */
MergeSort(arr, first, mid);
MergeSort(arr, mid+1,last);
Merge(arr,first,mid,last);
}
}
六、代码
#include <stdio.h>
#include <stdlib.h>
#define N 7
void Merge(int arr[],int low,int mid,int high)
{
int left_low=low; //左边序列的左下标
int left_high=mid;
int right_low=mid+1; //右边序列的左下标
int right_high=high;
int tmp[N],k=0,i; //数组tmp用来存放序列元素
while(left_low<=left_high&&right_low<=right_high) //当左右序列都有元素时执行循环
{
if(arr[left_low]<arr[right_low])
tmp[k++]=arr[left_low++]; //元素小的放进数组tmp
else
tmp[k++]=arr[right_low++];
}
if(left_low<=left_high){ //左边序列还有元素时
for(i=left_low;i<=left_high;i++)
tmp[k++]=arr[left_low++];
}
if(right_low<=right_high){ //右边序列还有元素时
for(i=right_low;i<=right_high;i++)
tmp[k++]=arr[right_low++];
}
for(i=0;i<high-low+1;i++){ //将数组tmp中的元素赋给数组arr,从而数组arr有序
arr[low+i]=tmp[i];
}
}
void MergeSort(int arr[],int first,int last)
{
int mid = 0;
if(first<last){
mid = (first+last)/2; /* 注意防止溢出 */
MergeSort(arr, first, mid);
MergeSort(arr, mid+1,last);
Merge(arr,first,mid,last);
}
}
int main(){
int i;
int a[N]={32,12,56,78,76,45,36};
printf ("排序前:");
for(i=0;i<N;i++)
printf("%d\t",a[i]);
MergeSort(a,0,N-1); // 排序
printf ("\n排序后:");
for(i=0;i<N;i++)
printf("%d\t",a[i]); printf("\n");
return 0;
}