排序--ShellSort 希尔排序
Posted 哇哩顾得
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了排序--ShellSort 希尔排序相关的知识,希望对你有一定的参考价值。
希尔排序 no 实现
希尔排序其实就是插入排序。只不过希尔排序在比较的元素的间隔不是1。 我们知道插入排序 都是 一个一个和之前的元素比较。发现比之前元素小就交换位置。但是希尔排序可能是和前第n个元素比较,如果发现比前第n个元素小就和前第n个元素交换位置。具体看下图
第一趟比较。n是为5。也就是说每个数和前面第5个数比较。如果发现小于前面第5个数的话。交换位置。
所以我们看到 72 比 592 小。 所以交换位置。 283 比 348 小。继续交换
第二趟比较。 n 是2。同理
最后一次比较。n是1 ,注意这个时候就是插入排序了。
这个 5 2 1 这种增量数字的选择到底是基于什么来选择的。其实我也不知道,一般的数字都可以,只不过性能不一定那么快。还有比如说4 排序了。 2 再排序的话 性能就会差一些。因为相对于4已经排序了的数组。已经有一部分的数组已经排好序了。
这里给出几个比较快的 排序增量的sequence
//Sedgewick 增量序列的最坏时间复杂度为 O(N4/3);平均时间复杂度约为 O(N7/6)。
//hi=max(9∗4^n−9∗2^n+1, 2^(n + 2) * (2^(n + 2) - 3)) + 1
//5 是由N = 0 得出来的
//28
private static int INCREMENT_SEQUENCE_SEDGEWICK[] = {
1,5,19,41,109,209,505,929,
2161,3905,8929,16001,36289,64769,146305,260609,
587521,1045505,2354689,4188161,9427969,16764929,37730305,67084289,
150958081,268386305,603906049,1073643521};
//Knuth sequence 3N + 1 , N 是之前的元素
//O(n^1.5)
//20
int INCREMENT_SEQUENCE_KNUTH[] = {
1,4,13,40,121,364,1093,3280,
9841,29524,88573,265720,797161,2391484,7174453,21523360,
64570081,193710244,581130733,1743392200};
具体的实现可以在这里看到 ->>>>>>https://github.com/Cheemion/algorithms/blob/master/src/com/algorithms/sort/ShellSort.java
这里还有关于什么shell排序很快的原因https://www.zhihu.com/question/24637339
Sedgewick 增量序列的ShellSort 最坏时间复杂度为 O(N4/3);平均时间复杂度约为 O(N7/6)
以上是关于排序--ShellSort 希尔排序的主要内容,如果未能解决你的问题,请参考以下文章