当前位置: 首页 > news >正文

归并排序(Merge Sort)

 

基本思想:

归并(Merge)排序法是将两个(或两个以上)有序表合并成一个新的有序表,即把待排序序列分为若干个子序列,每个子序列是有序的。然后再把有序子序列合并为整体有序序列。

归并排序示例:

 

 

合并方法:

若i>m 或j>n,转⑷ //其中一个子表已合并完,比较选取结束

  • //选取r[i]和r[j]较小的存入辅助数组rf
    如果r[i]<r[j],rf[k]=r[i]; i++; k++; 转⑵
    否则,rf[k]=r[j]; j++; k++; 转⑵
  • //将尚未处理完的子表中元素存入rf
    如果i<=m,将r[i…m]存入rf[k…n] //前一子表非空
    如果j<=n ,  将r[j…n] 存入rf[k…n] //后一子表非空
  • 合并结束。
 
//将r[i…m]和r[m +1 …n]归并到辅助数组rf[i…n]
void Merge(ElemType *r,ElemType *rf, int i, int m, int n)
{
	int j,k;
	for(j=m+1,k=i; i<=m && j <=n ; ++k){
		if(r[j] < r[i]) rf[k] = r[j++];
		else rf[k] = r[i++];
	}
	while(i <= m)  rf[k++] = r[i++];
	while(j <= n)  rf[k++] = r[j++];
}
 

归并的迭代算法

 

1 个元素的表总是有序的。所以对n 个元素的待排序列,每个元素可看成1 个有序子表。对子表两两合并生成n/2个子表,所得子表除最后一个子表长度可能为1 外,其余子表长度均为2。再进行两两合并,直到生成n 个元素按关键码有序的表。

 
void print(int a[], int n){
	for(int j= 0; j<n; j++){
		cout<<a[j] <<"  ";
	}
	cout<<endl;
}

//将r[i…m]和r[m +1 …n]归并到辅助数组rf[i…n]
void Merge(ElemType *r,ElemType *rf, int i, int m, int n)
{
	int j,k;
	for(j=m+1,k=i; i<=m && j <=n ; ++k){
		if(r[j] < r[i]) rf[k] = r[j++];
		else rf[k] = r[i++];
	}
	while(i <= m)  rf[k++] = r[i++];
	while(j <= n)  rf[k++] = r[j++];
	print(rf,n+1);
}

void MergeSort(ElemType *r, ElemType *rf, int lenght)
{ 
	int len = 1;
	ElemType *q = r ;
	ElemType *tmp ;
	while(len < lenght) {
		int s = len;
		len = 2 * s ;
		int i = 0;
		while(i+ len <lenght){
			Merge(q, rf,  i, i+ s-1, i+ len-1 ); //对等长的两个子表合并
			i = i+ len;
		}
		if(i + s < lenght){
			Merge(q, rf,  i, i+ s -1, lenght -1); //对不等长的两个子表合并
		}
		tmp = q; q = rf; rf = tmp; //交换q,rf,以保证下一趟归并时,仍从q 归并到rf
	}
}


int main(){
	int a[10] = {3,1,5,7,2,4,9,6,10,8};
	int b[10];
	MergeSort(a, b, 10);
	print(b,10);
	cout<<"结果:";
	print(a,10);

}
两路归并的递归算法
void MSort(ElemType *r, ElemType *rf,int s, int t)  
2.{   
3.    ElemType *rf2;  
4.    if(s==t) r[s] = rf[s];  
5.    else  
6.    {   
7.        int m=(s+t)/2;          /*平分*p 表*/  
8.        MSort(r, rf2, s, m);        /*递归地将p[s…m]归并为有序的p2[s…m]*/  
9.        MSort(r, rf2, m+1, t);      /*递归地将p[m+1…t]归并为有序的p2[m+1…t]*/  
10.        Merge(rf2, rf, s, m+1,t);   /*将p2[s…m]和p2[m+1…t]归并到p1[s…t]*/  
11.    }  
12.}  
13.void MergeSort_recursive(ElemType *r, ElemType *rf, int n)  
14.{   /*对顺序表*p 作归并排序*/  
15.    MSort(r, rf,0, n-1);  
16.}  

  

相关文章:

  • 装B技能GET起来!Apple Pay你会用了吗?
  • Tcp实现简单的大小写转换功能
  • uboot里读sd卡内容
  • Redis 主从复制
  • printk打印指针变量
  • 123
  • Bzoj 1984: 月下“毛景树” 树链剖分
  • 跨域访问解决方案:JSONP
  • maven工程打包jar以及java jar命令的classpath使用
  • ss 命令,第二代net-tools
  • Windows Iot:让Raspberry Pi跑起来(1)
  • js 点击弹窗以外 关闭弹窗
  • 几种经典排序算法的JS实现
  • solr多条件查询(二)
  • 网络基础(一)ARP!!!
  • 【前端学习】-粗谈选择器
  • Apache的80端口被占用以及访问时报错403
  • canvas 五子棋游戏
  • Material Design
  • MYSQL如何对数据进行自动化升级--以如果某数据表存在并且某字段不存在时则执行更新操作为例...
  • pdf文件如何在线转换为jpg图片
  • Tornado学习笔记(1)
  • zookeeper系列(七)实战分布式命名服务
  • 构建工具 - 收藏集 - 掘金
  • 看域名解析域名安全对SEO的影响
  • 漫谈开发设计中的一些“原则”及“设计哲学”
  • 前端代码风格自动化系列(二)之Commitlint
  • 深度学习入门:10门免费线上课程推荐
  • 使用iElevator.js模拟segmentfault的文章标题导航
  • 为视图添加丝滑的水波纹
  • 原生Ajax
  • ​​​​​​​Installing ROS on the Raspberry Pi
  • ​2020 年大前端技术趋势解读
  • #pragma预处理命令
  • #QT(智能家居界面-界面切换)
  • #快捷键# 大学四年我常用的软件快捷键大全,教你成为电脑高手!!
  • #前后端分离# 头条发布系统
  • (2022版)一套教程搞定k8s安装到实战 | RBAC
  • (附源码)流浪动物保护平台的设计与实现 毕业设计 161154
  • (三)centos7案例实战—vmware虚拟机硬盘挂载与卸载
  • (十)c52学习之旅-定时器实验
  • (十一)图像的罗伯特梯度锐化
  • (收藏)Git和Repo扫盲——如何取得Android源代码
  • (转)AS3正则:元子符,元序列,标志,数量表达符
  • *1 计算机基础和操作系统基础及几大协议
  • .NET 反射的使用
  • .NET 将多个程序集合并成单一程序集的 4+3 种方法
  • .NET 使用 XPath 来读写 XML 文件
  • .net/c# memcached 获取所有缓存键(keys)
  • .NET中GET与SET的用法
  • .Net转前端开发-启航篇,如何定制博客园主题
  • /usr/bin/env: node: No such file or directory
  • :中兴通讯为何成功
  • ?php echo $logosrc[0];?,如何在一行中显示logo和标题?
  • [20190113]四校联考