希尔排序的详细过程
希尔排序的详细过程:先取一个正整数d1数组元素放一组,组内进行直接插入排序;然后取d2三趟结果。希尔排序(Shell's Sort)是插入排序的一种又称“缩小增量排序”,是直接插入排序算法的一种更高效的改进版本。希尔排序是非稳定排序算法。该方法因D.L.Shell于1959年提出而得名。希尔排序是把记录按下标的一定增量分组,对每组使用直接插入排序算法排序;随着增量逐渐减少,每组包含的关键词越来越多,当增量减至1时,整个文件恰被分成一组,算法便终止。希尔排序按其设计者希尔的名字命名,该算法由希尔在1959年所发表的论文“A high-speed sorting procedure”中所描述。希尔排序的优劣本质上讲,希尔排序算法是直接插入排序算法的一种改进,减少了其复制的次数,速度要快很多。原因是,当n值很大时数据项每一趟排序需要移动的个数很少,但数据项的距离很长。当n值减小时每一趟需要移动的数据增多,此时已经接近于它们排序后的最终位置。正是这两种情况的结合才使希尔排序效率比插入排序高很多。Shell算法的性能与所选取的分组长度序列有很大关系。只对特定的待排序记录序列,可以准确地估算关键词的比较次数和对象移动次数。
希尔排序的详细过程
把记录按步长 gap 分组,对每组记录采用直接插入排序方法进行排序。随着步长逐渐减小,所分成的组包含的记录越来越多,当步长的值减小到 1 时,整个数据合成为一组,构成一组有序记录,则完成排序。我们来通过演示图,更深入的理解一下这个过程。希尔排列希尔排序又叫递减增量排序算法,它是在直接插入排序算法的基础上进行改进而来的,综合来说它的效率肯定是要高于直接插入排序算法的;希尔排序是一种不稳定的排序算法。希尔排序由唐纳德·希尔(Donald Shell)发明并于1959年公布,因此得名希尔排序。希尔算法
排序算法-7---希尔排序
希尔排序(Shellsort),也称递减增量排序算法,是一种典型的插入排序算法,通过对原始序列进行分组进行排序。希尔排序是非稳定排序算法。
希尔排序是基于插入排序的以下两点性质而提出改进方法的:
希尔排序的基本思想就是:先将整个待排序的记录序列分割成为若干子序列分别进行直接插入排序,待整个序列中的记录“基本有序”时,再对全体记录进行依次直接插入排序。
矩阵的列数取决于步长序列(step sequence)
比如,如果步长序列为{1,5,19,41,109...}.. 就代表依次分成109列、41列、 19列、 5列、1列进行排序
不同的步长序列,执行效率也不同
1、选择一个增量序列t1,t2,…,tk,其中对于i>j,有ti>tj,tk=1;(增量因子有多种取法,最简单的是t(i+1) = ti/2)
2、按增量序列个数k,对序列进行k 趟排序;
3)每趟排序,根据对应的增量ti,将待排序列分割成若干长度为m 的子序列,分别对各子表进行直接插入排序。仅增量因子为1 时,整个序列作为一个表来处理,表长度即为整个序列的长度。
**希尔排序的执行时间依赖于增量序列。 **
希尔排序耗时的操作有:比较 + 后移赋值。
时间复杂度情况如下:(n指待排序序列长度)
希尔排序是按照不同步长对元素进行插入排序,当刚开始元素很无序的时候,步长最大,所以插入排序的元素个数很少,速度很快;当元素基本有序了,步长很小,插入排序对于有序的序列效率很高。所以,希尔排序的时间复杂度会比O(n²)好一些。
希尔算法的性能与所选取的增量(分组长度)序列有很大关系。只对特定的待排序记录序列,可以准确地估算比较次数和移动次数。想要弄清比较次数和记录移动次数与增量选择之间的关系,并给出完整的数学分析,至今仍然是数学难题。
希尔算法在最坏的情况下和平均情况下执行效率相差不是很多,与此同时快速排序在最坏的情况下执行的效率会非常差。希尔排序没有快速排序算法快,因此中等大小规模表现良好,对规模非常大的数据排序不是最优选择。
(注:专家们提倡,几乎任何排序工作在开始时都可以用希尔排序,若在实际使用中证明它不够快,再改成快速排序这样更高级的排序算法。)
由于多次插入排序,我们知道一次插入排序是稳定的,不会改变相同元素的相对顺序,但在不同的插入排序过程中,相同的元素可能在各自的插入排序中移动,最后其稳定性就会被打乱,所以希尔排序是不稳定的。
备注:希尔排序的时间性能优于直接插入排序
参考文章
经典排序算法(5)——希尔排序算法详解
排序:希尔排序(算法)
05《算法入门教程》希尔排序
本节内容是排序算法系列之一: 希尔排序 ,主要讲解了希尔排序的主体思路,选取了一个待排序的数字列表对希尔排序算法进行了演示,给出了希尔排序算法的 Java 代码实现,帮助大家可以更好的理解希尔排序算法。 希尔排序(Shell Sort),是计算机科学与技术领域中较为简单的一种排序算法。 希尔排序是插入排序的一种,有时候也被称为 “缩小增量排序”。它是插入排序的改进版,与插入排序的不同之处在于,希尔排序会优先比较距离较远的元素。希尔排序是按照其设计者希尔(Donald Shell)的名字命名而来,并于 1959 年公布出来。 在介绍完希尔排序之后,我们一起来看一下希尔排序的实现步骤具体是什么样的吧。这里我们假设待排序的序列为 [9,2,11,7,12,5],我们按照从小到大的序列进行排序。 选择一个增量序列 k1,k2, … km,其中 k1>k2>…km=1,即增量序列大小依次减小,并且最后一个增量序列大小为 1。 按照增量序列的个数 m,对整个待排序序列进行 m 趟排序。 每一趟排序,根据对应的增量 ki,需要将待排序的序列分成对应长度的子序列,分别在子序列上面进行直接插入排序。当且仅当增量序列为 1 时,整个序列作为一个整体处理。 其实,上面的 步骤 1 和 步骤 2 都是在排序之前进行的处理,选择对应的增量。上面的 步骤 3 每执行一次,就相当于是进行了一次插入排序,只是每次都会选择一个增量,将整个待排序序列按照增量进行划分,然后在对应增量上面进行插入排序。接下来,让我们用上面的待排序数字队列 [9,2,11,7,12,5] 进行整个算法步骤的排序演示工作。 按照 2.1 节的排序步骤,我们需要先选择对应的希尔排序中的增量值,按照一般性的原则,我们可以将增量按照待排序的序列长度依次整除 2,直到增量为 1 停止,得到对应的增量。如下: 接着,我们调用 2.1 中的 步骤 2, 步骤 3 ,按照增量值的取法,依次进行对应序列的插入排序,首先我们取增量值为 3,对应排序示例如下: 在完成增量为 3 的插入排序之后,我们接着进行增量为 1 的插入排序,这个步骤其实跟我们之前的插入排序步骤完全一致。整个过程如下: 从上面的示例可以看出,其实整个希尔排序的过程,就是根据增量大小依次进行插入排序,本质上还是针对插入排序的一种优化。 在说明希尔排序的整个过程之后,接下来,我们看看如何用 Java 代码实现希尔排序算法。 运行结果如下: 代码中的第 8 行初始化一个需要排序的数组,后面按照从小到大的排序规则,实现了数组的排序。第 12 行至 30 行是整个希尔排序的流程。第 14 行代码表示希尔排序中的增量每次整除 2 取得,第 17 行至 25 行是一个 for 循环结构,表明按照增量进行插入排序。最后第 32 行代码输出排序好的数组。 本节主要学习了希尔排序算法,通过本节课程的学习,需要熟悉希尔排序的算法流程,知道希尔排序算法的实现思路,可以自己用代码实现希尔排序算法。至此,我们已经学习了排序算法中的冒泡排序、插入排序、选择排序、希尔排序。