算法导论2.3从归并排序了解分治思想

归并排序

归并排序中最重要的就是将两个已排序子数组进行归并,我们选择重复比较每个子数组得大小,将小的重新放置到原始组。在每个临时子数组的最后设置哨兵值,设置为一个特殊值INT_MAX,这样可以保障当一个子数组到达哨兵值后永远会将另一个子数组赋值给原数组,除非两个子数组都到达哨兵值。当这种情况出现,两个子数组均已被赋值给原数组,原数组已被合并为一个新的排序数组。

#include <stdio.h>
#include <limits.h>
void merge(int*arr,int p,int q,int r){
	int n1=q-p+1;
	int n2=r-q;
	int left[n1+1];
	int right[n2+1];
	for(int i=0;i<n1;i++)
		left[i]=arr[p+i];		//arr[p] 到 arr[q];
	for(int j=1;j<=n2;j++)		
		right[j-1]=arr[q+j];		//arr[q+1]到arr[r];
	left[n1]=INT_MAX;
	right[n2]=INT_MAX;
	int i=0,j=0;
	for(int k=p;k<=r;k++){
		if(left[i]<=right[j]){
			arr[k]=left[i];
			i++;
		}
		else{
			arr[k]=right[j];
			j++;
		}
	}
}

void mergeSort(int* arr,int p,int r){
	int q;
	if(p<r){
		q=(p+r)/2;
		mergeSort(arr,p,q);
		mergeSort(arr,q+1,r);
		merge(arr,p,q,r);
	}
}

int main(void){
	int arr[]={2,4,5,6,1,2,9,0};
	mergeSort(arr,0,7);
	for(int i=0;i<8;i++)
		printf("%d ",arr[i]);
	return 0;
}
发布了19 篇原创文章 · 获赞 1 · 访问量 3134

猜你喜欢

转载自blog.csdn.net/qq_41603639/article/details/104729774