并归排序是属于快速排序法的一种,基本思想分为三步如下。
第一步:根据递归算法不断进行拆分,每一次都把每个子序列拆分为两个长度相等的子序列(有时候会多出一个元素来就像图中第二行)
如图(这一步是到图片中第四行)
第二步:当拆分到不能拆分时,进行排序,而我们通常递归到最后每个序列的元素只有一个所以并不需要排序。
第三步:每一次都将原本拆分过的两部分合并在一起,这个过程是并归排序的主要步骤,当我们合并两个有序序列的时候会进行比较如下图
这个图的意思就是b将会是一个temp空间,我们比较完成后会把较小的元素放在temp空间里。
代码展示:
#include <bits/stdc++.h>
using namespace std;
const int maxn=100000;
int a[maxn+10],temp[maxn+10];
void msort(int l,int r)/*传入左边界和右边界*/
{
if(l>=r)
return ;
int mid= l+r >> 1;/*确定中点*/
msort(l,mid);/*这两行就是在进行第一步了*/
msort(mid+1,r);/*注意mid位置不要重复*/
int k=0,i=l,j=mid+1;/** * */
while(i<=mid&&j<=r)/*第三步*/
{
if(a[i]<=a[j])/*符合条件了*/
{
temp[k++]=a[i++];
}
else
{
temp[k++]=a[j++];/*毕竟会有一个大一个小*/
}
}
while(i<=mid)/*这两个while是把所有剩下的零碎元素加到temp中*/
{
temp[k++]=a[i++];
}
while(j<=r)
{
temp[k++]=a[j++];
}
for(i=l,j=0;i<=r;i++,j++)/*把已经排序完毕的temp再复制给a*/
{
a[i]=temp[j];
}
}
int main()
{
int t;
for(cin>>t;t;t--)
{
int n;
cin>>n;
for(int i=0;i<n;i++)
{
a[i]=n-i;
}
msort(0,n-1);
for(int i=0;i<n;i++)
{
cout<<a[i]<<" ";
}
cout<<endl;
}
}
下面是模板引用自CSDN博客
void merge_sort(int q[], int l, int r)
{
if (l >= r) return;
int mid = l + r >> 1;//确定中点
merge_sort(q, l, mid);//递归排左边
merge_sort(q, mid + 1, r);//递归排右边
int k = 0, i = l, j = mid + 1;//k表示表示当前tmp中有多少个数,i和j两个指针:表示左右两边的起点
while (i <= mid && j <= r)//小于等于左半边的边界&&小于等于右半边的边界
if (q[i] <= q[j]) tmp[k ++ ] = q[i ++ ];//如果(q[i] <= q[j]),把q[i]拿过来放入数组
else tmp[k ++ ] = q[j ++ ];//否则把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];//最后吧tmp里边的数复制回q里边
}