归并排序
日常膜拜dalao:财神万岁!!!!!!!!!!!!!!!!!
日常凌晨三点水博客。。写这些入门的休息一会,主要是为了传以前写的一些东西。。
话说这个归并排序是对新手最不友好的一种排序方式之一。。(还有快速排序)
言归正传
什么是归并排序?
归并排序是一种效率较高的排序方法,它分为拆分和合并两大部分,先拆后合。
拆分,就是将一堆无序的数拆成单个,方便合并。
合并,就是将拆分好的数按照排序规则再拼凑起来。
详细解释请看下图:
拆分:
合并:
看完这两幅图你应该明白了,归并排序原来就是将一堆数字分开,再合成有序的数列
其实,这就是分治的思想,将大问题化小问题,将每个最小的问题处理好,合并起来大问题也就处理好了~
古人云:大事化小,小事化了
代码
在明白了归并排序的基本思想后,我们来看代码:
(解释都在代码里面了,我好懒qwq)
#include<iostream>//归并排序,先拆后合
#include<cstring>
int a[1500];
using namespace std;
void hebing(int *a,int l,int mid,int r)//合并,从a数组的下标l到r中间为m的部分合并
{
int b[1500];//临时存放合并结果的数组,否则a数组会乱
memset(b,0,sizeof(int)) ;//清零b数组
int k=0;
int i=l;int j=mid;
while(i<mid&&j<=r)//当mid的左右两端都剩数字时,任意一边放完了都会退出
{
if(a[i]<=a[j])//小的往前放
b[k++]=a[i++];
else
b[k++]=a[j++];
}
while(j<=r) b[k++]=a[j++];//注意这一句和下面一句一次只合并会有其中一个执行
while(i<mid) b[k++]=a[i++];//把剩下的没放完的一边也扔进b里面
for(int i=l;i<=r;i++) a[i]=b[i-l];//把b还给a
}
void guibing(int *a,int start,int end){//拆分 (原谅我可怜的英语)
//(注意这是个递归)
if(start==end) return;//拆到最小不能再拆
int mid=(start+end)/2;
guibing(a,start,mid);//拆左边
guibing(a,mid+1,end);//拆右边
hebing(a,start,mid+1,end);//合并
}
int main(){
int n;
cin>>n;
for(int i=1;i<=n;i++){
cin>>a[i];
}
guibing(a,1,n);
for(int i=1;i<=n;i++)
cout<<a[i]<<" ";
return 0;
}
推荐题目
洛谷p1908逆序对
洛谷p1309瑞士轮
怎么样是不是超级简单
本文若有不道处欢迎评论,
感谢各位神犇对本蒟蒻的支持!qwq