归并排序算法也算大家常用的一种方法,萌新周周在这里用C语言给大家简单总结一下归并排序算法吧。
关键:分治。
原理步骤:1.确定分界点,找下标的中间值 2.递归排序right和left 3.归并合二为一,其中第三个步骤是关键。
先把左边右边排完序,然后归并。
废话不多说,直接放代码吧,重要细节都有注释:
#include <iostream>
using namespace std;
const int N=1000010;
int n;
int q[N],tmp[N];//tmp数组存放左边和右边递归后的数
void merge_sort(int q[],int l,int r)
{
if(l>=r)return;//区间里的个数为1或0时返回
int mid=l+r>>1;//mid=(left+right)>>1相当于mid=(left+right)/2
merge_sort(q,l,mid),merge_sort(q,mid+1,r);//分别递归左边和右边 ,左边和右边都排完序了
int k=0,i=l,j=mid+1;//k代表和并的个数,取i,j两个指针变量,分别指向左边和右边的第一个数
while(i<=mid&&j<=r)
if(q[i]<=q[j]) tmp[k++]=q[i++];//如果左边数小于右边数,则就把左边的数拿进归并后的数组里面,左边指针往后移一位,右边指针不动
else tmp[k++]=q[j++];//以上同理
while(i<=mid)tmp[k++]=q[i++];//如果右边数的指针已经指到最后一位,左边还未指完,直接把左边里的数拿进归并数组里
while(j<=r)tmp[k++]=q[j++];//右边情况同理;
for(i=l,j=0;i<=r;i++,j++)q[i]=tmp[j];//最后把临时数组里的数拿进q数组里面
}
int main()
{
scanf("%d",&n);
for(int i=0;i<n;i++)scanf("%d",&q[i]);
merge_sort(q,0,n-1);
for(int i=0;i<n;i++)printf("%d ",q[i]);
return 0;
}