三十分钟理解:双调排序Bitonic Sort,适合并行计算的排序算法
欢迎转载,转载请注明:本文出自Bin的专栏blog.csdn.net/xbinworld
技术交流QQ群:433250724,欢迎对算法、技术、应用感兴趣的同学加入
双调排序是data-independent的排序, 即比较顺序与数据无关的排序方法, 特别适合做并行计算,例如用GPU、fpga来计算。
1、双调序列
在了解双调排序算法之前,我们先来看看什么是双调序列。 双调序列是一个先单调递增后单调递减(或者先单调递减后单调递增)的序列。
2、Batcher定理
将任意一个长为2n的双调序列A分为等长的两半X和Y,将X中的元素与Y中的元素一一按原序比较,即a[i]与a[i+n] (i < n)比较,将较大者放入MAX序列,较小者放入MIN序列。则得到的MAX和MIN序列仍然是双调序列,并且MAX序列中的任意一个元素不小于MIN序列中的任意一个元素[2]。
3、双调排序
假设我们有一个双调序列,则我们根据Batcher定理,将该序列划分成2个双调序列,然后继续对每个双调序列递归划分,得到更短的双调序列,直到得到的子序列长度为1为止。这时的输出序列按单调递增顺序排列。
见下图:升序排序,具体方法是,把一个序列(1…n)对半分,假设n=2^k,然后1和n/2+1比较,小的放上,接下来2和n/2+2比较,小的放上,以此类推;然后看成两个(n/2)长度的序列,因为他们都是双调序列,所以可以重复上面的过程;总共重复k轮,即最后一轮已经是长度是2的序列比较了,就可得到最终的排序结果。
双调排序示意图[1]:
4、任意序列生成双调序列
前面讲了一个双调序列如何排序,那么任意序列如何变成一个双调序列呢?
这个过程叫Bitonic merge, 实际上也是divide and conquer的思路。 和前面sort的思路正相反, 是一个bottom up的过程——将两个相邻的,单调性相反的单调序列看作一个双调序列, 每次将这两个相邻的,单调性相反的单调序列merge生成一个新的双调序列, 然后排序(同3、双调排序)。 这样只要每次两个相邻长度为n的序列的单调性相反, 就可以通过连接得到一个长度为2n的双调序列,然后对这个2n的序列进行一次双调排序变成有序,然后在把两个相邻的2n序列合并(在排序的时候第一个升序,第二个降序)。 n开始为1, 每次翻倍,直到等于数组长度, 最后就只需要再一遍单方向(单调性)排序了。
以16个元素的array为例,
1. 相邻两个元素合并形成8个单调性相反的单调序列,
2. 两两序列合并,形成4个双调序列,分别按相反单调性排序
3. 4个长度为4的相反单调性单调序列,相邻两个合并,生成两个长度为8的双调序列,分别排序
4. 2个长度为8的相反单调性单调序列,相邻两个合并,生成1个长度为16的双调序列,排序
示意图[1]:
详细Bitonic merge图(本图只画到生成一个16长的双调序列,最后排序没有画出):
最后再放一个8个元素排序的示意图[5]:
5、非2的幂次长度序列排序
这样的双调排序算法只能应付长度为2的幂的数组。那如何转化为能针对任意长度的数组呢?一个直观的方法就是使用padding。即使用一个定义的最大或者最小者来填充数组,让数组的大小填充到2的幂长度,再进行排序。最后过滤掉那些最大(最小)值即可。这种方式会使用到额外的空间,而且有时候padding的空间比较大(如数组长度为1025个元素,则需要填充到2048个,浪费了大量空间)。但是这种方法比较容易转化为针对GPU的并行算法。所以一般来说,并行计算中常使用双调排序来对一些较小的数组进行排序[3]。 如果要考虑不用padding,用更复杂的处理方法,参考[4] n!=2^k的双调排序网络,本文略。
参考资料
[1] CUDA(六). 从并行排序方法理解并行化思维——冒泡、归并、双调排序的GPU实现, http://blog.csdn.net/abcjennifer/article/details/47110991
[2] 并行计算】Bitonic Sort(双调排序)基础, http://blog.csdn.net/jiange_zh/article/details/49533477
[3] 双调排序:从串行到并行,以及OpenCL上的实现, http://blog.csdn.net/bryanlai0720/article/details/45094675
[4] n!=2^k的双调排序网络, http://blog.csdn.net/ljiabin/article/details/8630627
[5] 分段双调排序实现, http://blog.csdn.net/u014226072/article/details/56840243
三十分钟理解:双调排序Bitonic Sort,适合并行计算的排序算法的更多相关文章
- [转载]三十分钟理解:线性插值,双线性插值Bilinear Interpolation算法
[转载]三十分钟理解:线性插值,双线性插值Bilinear Interpolation算法 来源:https://blog.csdn.net/xbinworld/article/details/656 ...
- 简单选择排序 Selection Sort 和树形选择排序 Tree Selection Sort
选择排序 Selection Sort 选择排序的基本思想是:每一趟在剩余未排序的若干记录中选取关键字最小的(也可以是最大的,本文中均考虑排升序)记录作为有序序列中下一个记录. 如第i趟选择排序就是在 ...
- 【转载】双调排序Bitonic Sort,适合并行计算的排序算法
双调排序是data-independent的排序, 即比较顺序与数据无关的排序方法, 特别适合做并行计算,例如用GPU.fpga来计算. 1.双调序列 在了解双调排序算法之前,我们先来看看什么是双调序 ...
- 三十分钟理解博弈论“纳什均衡” -- Nash Equilibrium
欢迎转载,转载请注明:本文出自Bin的专栏blog.csdn.net/xbinworld. 技术交流QQ群:433250724,欢迎对算法.技术感兴趣的同学加入. 纳什均衡(或者纳什平衡),Nash ...
- 三十分钟理解:线性插值,双线性插值Bilinear Interpolation算法
线性插值 先讲一下线性插值:已知数据 (x0, y0) 与 (x1, y1),要计算 [x0, x1] 区间内某一位置 x 在直线上的y值(反过来也是一样,略): y−y0x−x0=y1−y0x1−x ...
- [重磅]Deep Forest,非神经网络的深度模型,周志华老师最新之作,三十分钟理解!
欢迎转载,转载请注明:本文出自Bin的专栏blog.csdn.net/xbinworld. 技术交流QQ群:433250724,欢迎对算法.技术感兴趣的同学加入. 深度学习最大的贡献,个人认为就是表征 ...
- 三十分钟理解计算图上的微积分:Backpropagation,反向微分
神经网络的训练算法,目前基本上是以Backpropagation (BP) 反向传播为主(加上一些变化),NN的训练是在1986年被提出,但实际上,BP 已经在不同领域中被重复发明了数十次了(参见 G ...
- python 字典排序 关于sort()、reversed()、sorted()
一.Python的排序 1.reversed() 这个很好理解,reversed英文意思就是:adj. 颠倒的:相反的:(判决等)撤销的 print list(reversed(['dream','a ...
- <转>python字典排序 关于sort()、reversed()、sorted()
一.Python的排序 1.reversed() 这个很好理解,reversed英文意思就是:adj. 颠倒的:相反的:(判决等)撤销的 print list(reversed(['dream','a ...
随机推荐
- php5.6安装gd库
rpm -Uvh http://ftp.iij.ad.jp/pub/linux/fedora/epel/6/x86_64/epel-release-6-8.noarch.rpm rpm -Uvh ht ...
- testng多线程并行执行测试
testng多线程并行执行测试 testng多线程并行执行测试 并行(多线程)技术在软件术语里被定义为软件.操作系统或者程序可以并行地执行另外一段程序中多个部分或者子组件的能力.TestNG允许我们以 ...
- Git 系列——第一步安装 Git
之前也没有用过什么版本控制的工具,唯一用过的就是 SVN 了,不过也只是简单的使用而已,比如写好代码就签入,没了?是的,没了. 于是接触到了 Git 这个分布式版本控制软件,接下来就让我们好好学习,天 ...
- poj1106 Transmitters
地址:http://poj.org/problem?id=1106 题目: Transmitters Time Limit: 1000MS Memory Limit: 10000K Total S ...
- 【android】如何让WebView对Video标签的支持更强力
先说结论:各个产商对HTML5特性支持的程度不一样,用默认的WebChromeClient不能普遍适用. 因此咱基于GITHUB上一个VideoEnabledWebView库做了自己的封装,在魅族.华 ...
- nmon监控Linux服务器系统资源
本文转自:http://www.cnblogs.com/hyzhou/archive/2011/12/29/2305860.html 在实际的测试过程中,Loadrunner监控Linux系统资源不太 ...
- 微信 audio 获取 duration 为 NaN 的解决方法
先加load() myaudio.load(); myaudio.oncanplay = function () { alert(myaudio.duration); } load() 方法用于在更改 ...
- UVa 10635 王子和公主(LCS转LIS)
https://vjudge.net/problem/UVA-10635 题意: 有两个长度分别为p+1和q+1的序列,每个序列中的各个元素互不相同,且都是1~n^2之间的整数.两个序列的第一个元素均 ...
- 安装 bochs
sudo apt-get install bochs 以后接着安装bochs-x
- Iterator(迭代器)
意图: 提供一种方法顺序访问一个聚合对象中各个元素, 而又不需暴露该对象的内部表示. 适用性: 访问一个聚合对象的内容而无需暴露它的内部表示. 支持对聚合对象的多种遍历. 为遍历不同的聚合结构提供一个 ...