更高效的MergeSort--稍微优化
0. 简介
本文简要介绍一下比传统MergeSort更高效的算法,在原来的算法Merge基础上,少发生一半拷贝。欢迎探讨,感谢阅读。
原文链接如下:http://loverszhaokai.com/posts/More-Efficient-MergeSort/
1. Reference
原文链接
Introuction to Algorithms
https://github.com/loverszhaokai/ALG/blob/master/src/sort.cc
2. MergeSort
void merge(int a[], int b[], const int left, const int middle,
const int right) {
int li, ri, i;
li = left;
ri = middle + 1;
i = 0;
while (li <= middle && ri <= right) {
if (a[li] < a[ri])
b[i++] = a[li++];
else
b[i++] = a[ri++];
}
while (li <= middle)
b[i++] = a[li++];
while (ri <= right)
b[i++] = a[ri++];
}
void copy(int dst[], int dleft, int src[], int sleft, int sright) {
memcpy(dst + dleft, src + sleft,
sizeof(int) * (sright - sleft + 1));
}
void _merge_sort(int a[], int b[], const int left, const int right) {
if (left >= right)
return;
int middle = (left + right) / 2;
_merge_sort(a, b, left, middle);
_merge_sort(a, b, middle + 1, right);
merge(a, b, left, middle, right);
copy(a, left, b, 0, right - left);
}
void merge_sort(int a[], const int size) {
int *b = (int *)malloc(size * sizeof(int));
_merge_sort(a, b, 0, size - 1);
free(b);
}
3. More Efficient MergeSort
We can save some time by copy half when merge(). In merge(), we copy from
left to right, but in MergeKai() we can only copy from left to
middle. The merge() has NlgN duplications which the MergeKai() has
1/2 * NlgN duplications.

normal merge sort

more efficient merge sort
Just as the previous example, the efficient merge sort does not need to copy
1, 3, 7, 8 to the assit array.
// Merge the two list in [left, mid], and (mid, right]. Then, write
// the result to [left, right]
static void MergeKai(int a[], int assist[], const int left,
const int mid, const int right) {
int l = left;
int r = mid + 1;
int assist_index = 0;
// Copy [left, mid] to assit[0, mid - left]
memcpy(assist, a + left, (mid - left + 1) * sizeof(int));
while (assist_index <= mid - left && r <= right) {
if (assist[assist_index] <= a[r]) {
a[l++] = assist[assist_index++];
continue;
} else if (assist[assist_index] > a[r]) {
a[l++] = a[r++];
}
}
while (assist_index <= mid - left) {
a[l++] = assist[assist_index++];
}
while (r <= right) {
a[l++] = a[r++];
}
}
static void MergeSortKaiImpl(int a[], int assist[], const int left,
const int right) {
if (left >= right) {
return;
}
const int mid = (left + right) / 2;
MergeSortKaiImpl(a, assist, left, mid);
MergeSortKaiImpl(a, assist, mid + 1, right);
MergeKai(a, assist, left, mid, right);
}
void MergeSortKai(int a[], const int size) {
int* assist= (int *)malloc(size * sizeof(int));
MergeSortKaiImpl(a, assist, 0, size - 1);
free(assist);
}
4. Experiments
source:
https://github.com/loverszhaokai/ALG/blob/master/src/sort.cc
https://github.com/loverszhaokai/ALG/blob/master/test/sort_test.cc
result:
It takes 1524.61 ms to generate arrays: 1000000 * 20
Sort Function Total Run Time Array Size
---------------------------------------------------------------------
merge_sort_iteratively 826 ms 1000000 * 20
merge_sort 840 ms 1000000 * 20
MergeSortIterativelyKai 826 ms 1000000 * 20
MergeSortKai 809 ms 1000000 * 20
It takes 15028.2 ms to generate arrays: 10000000 * 20
Sort Function Total Run Time Array Size
---------------------------------------------------------------------
merge_sort_iteratively 8717 ms 10000000 * 20
merge_sort 8820 ms 10000000 * 20
MergeSortIterativelyKai 8425 ms 10000000 * 20
MergeSortKai 8389 ms 10000000 * 20
It takes 1929.31 ms to generate arrays: 100000 * 200
Sort Function Total Run Time Array Size
---------------------------------------------------------------------
merge_sort_iteratively 1245 ms 100000 * 200
merge_sort 1347 ms 100000 * 200
MergeSortIterativelyKai 1246 ms 100000 * 200
MergeSortKai 1275 ms 100000 * 200
更高效的MergeSort--稍微优化的更多相关文章
- 使jQuqer更高效的方法
讨论 jQuery 和 javascript 性能的文章并不罕见.然而,本文我计划总结一些速度方面的技巧和我本人的一些建议,来提升你的 jQuery 和 javascript 代码.好的代码会带来速度 ...
- 如何使代码审查更高效【摘自InfoQ】
代码审查者在审查代码时有非常多的东西需要关注.一个团队需要明确对于自己的项目哪些点是重要的,并不断在审查中就这些点进行检查. 人工审查代码是十分昂贵的,因此尽可能地使用自动化方式进行审查,如:代码 ...
- 如何让windows更高效?
首先解释一下个标题: "让windows更高效,既指让windows更友好更优化,也指可以让使用windows来工作或学习的人更高效的工作学习." 解释下本文的动机: 指导我自己或 ...
- 更强、更稳、更高效:解读 etcd 技术升级的三驾马车
点击下载<不一样的 双11 技术:阿里巴巴经济体云原生实践> 本文节选自<不一样的 双11 技术:阿里巴巴经济体云原生实践>一书,点击上方图片即可下载! 作者 | 陈星宇(宇慕 ...
- CesiumLab V1.4 分类3dtiles生成(倾斜单体化、楼层房间交互)我记得我是写过一篇关于倾斜单体化的简书文章的,但是现在找不到了。不过找不到也好,就让他随风逝去吧,因为当时我写那篇文章的时候,就发现了cesium实际是有另一种更高效的单体化。就下面这个示例https://cesiumjs.org/Cesium/Build/Apps/Sandcastle/index.html?src=
我记得我是写过一篇关于倾斜单体化的简书文章的,但是现在找不到了.不过找不到也好,就让他随风逝去吧,因为当时我写那篇文章的时候,就发现了cesium实际是有另一种更高效的单体化.就下面这个示例 http ...
- [源码解析]为什么mapPartition比map更高效
[源码解析]为什么mapPartition比map更高效 目录 [源码解析]为什么mapPartition比map更高效 0x00 摘要 0x01 map vs mapPartition 1.1 ma ...
- 阿里面试:MySQL如何设计索引更高效?
有情怀,有干货,微信搜索[三太子敖丙]关注这个不一样的程序员. 本文 GitHub https://github.com/JavaFamily 已收录,有一线大厂面试完整考点.资料以及我的系列文章. ...
- K8s 如何提供更高效稳定的编排能力?K8s Watch 实现机制浅析
关于我们 更多关于云原生的案例和知识,可关注同名[腾讯云原生]公众号~ 福利: ①公众号后台回复[手册],可获得<腾讯云原生路线图手册>&<腾讯云原生最佳实践>~ ②公 ...
- Karmada v1.3:更优雅 更精准 更高效
摘要:最新发布的1.3版本中,Karmada重新设计了应用跨集群故障迁移功能,实现了基于污点的故障驱逐机制,并提供平滑的故障迁移过程,可以有效保障服务迁移过程的连续性(不断服). 本文分享自华为云社区 ...
随机推荐
- Nginx学习之keepalive
当然,在nginx中,对于http1.0与http1.1也是支持长连接的.什么是长连接呢?我们知道,http请求是基于TCP协议之上的,那么,当客户端在发起请求前,需要先与服务端建立TCP连接,而每一 ...
- iOS自带分享
NSArray *activityItems; if (self.sharingImage != nil) { activityItems = @[self.sharingText, self.sha ...
- 一个简单web系统的接口性能分析及调优过程
在测试一个简单系统接口性能压力时,压到一定数量,程序总是崩溃,查看相关机器相关数据时,CPU.内存.IO占用均不高,问题自然出现在其它地方先介绍下系统部件架构 Resin版本为:[root@local ...
- R的any和all
> x<-1:10 > any(x>8) [1] TRUE > all(x>8) [1] FALSE
- 单引号、双引号、int和char
首先说一下C语言中用单引号和双引号的不同(一直搞不清楚): 单引号代表的是一个整数,而这个整数的值是编译器所采用的字符集中的字符序列对应的值.所以一般'A'和ASCII中的65意义相同.对于双引号定义 ...
- ELk之使用kibana展示访问IP地图
参考文档:http://blog.51cto.com/ls40905250/1915280 https://blog.csdn.net/zsjwish/article/details/79792212 ...
- hdu5955 Guessing the Dice Roll【AC自动机】【高斯消元】【概率】
含高斯消元模板 2016沈阳区域赛http://acm.hdu.edu.cn/showproblem.php?pid=5955 Guessing the Dice Roll Time Limit: 2 ...
- opencv学习笔记霍夫变换——直线检测
参考大佬博文:blog.csdn.net/jia20003/article/details/7724530 lps-683.iteye.com/blog/2254368 openCV里有两个函数(比较 ...
- XTU 1267 - Highway - [树的直径][2017湘潭邀请赛H题(江苏省赛)]
这道题可能有毒……总之一会儿能过一会儿不能过的,搞的我很心烦…… 依然是上次2017江苏省赛的题目,之前期末考试结束了之后有想补一下这道题,当时比较懵逼不知道怎么做……看了题解也不是很懂……就只好放弃 ...
- Kettle 4.2源码分析第一讲--Kettle 简介
Pentaho Data Integration(PDI)简介 1. PDI结构简介 图 1‑1 PDI核心组件 Spoon是构建ETL Jobs和Transformations的工具.Spoon可以 ...