数据结构-第八章(8.2插入排序)

知识总览

思想:插入排序是一种简单直观的排序方法,其基本思想是每次将一个待排序的记录按关键字大小插入前面已排好序的子序列。

1.直接插入排序

一、直接插入排序思想
我们已经有了一个排好的序列,我们现在要取一个数插入到这个有序的序列里让其插入后的记录数加一的序列也是有序的。我们把待排序列的所有数都依次插好后最后的序列就是有序的。类似我们一张一张摸牌,每次整理好再摸下一张牌。

  • 插入第二个数使它和第一个数这个有序的序列合并为一个记录数加一的有序序列: 将序列的第一个数看做一个有序的序列,然后把第二个数插进来。(这里没有必要把第一个数插入空序列中,因为只有一个数本身就是有序的)。如何保证插入一个数之后序列是有序的呢?具体操作为让这个数与有序序列的最大的数(即最后位置)比较,如果比最大的数还大,那它就是新序列最大的数。如果比最大的数小的话,我们交换这两个数的位置,让要插入的数与变短的有序序列继续比较,直到不再交换那么整个新序列就有序了。 
  • 插入第三个数直至插入第N-1个数我们就排好了N个数的序列:每插入一个数我们得到一个有序的序列,直到插入最后一个数我们得到有序的待排序列。

直接插入排序按不同视角被分到:

  • 稳定排序
  • 简单排序
  • 内排序
  • 插入排序

代码

带哨兵

明白待哨兵的意义:

不用每次判断j>=0 

课本上的代码是把Tmp设为A[0],名为哨兵位,好处是减少比较次数提高算法效率,不用在第二个for内判断i>0这种越界条件了,因为不会越界,最多将要插入的数移动到A[1]的位置,然后此时A[0]和A[1]都是要插入的数,第二个for循环终止。

最好情况:本来有序

最差情况:为逆序(每个都要进行比较)

例题:对n个元素的顺序表采用直接插入排序算法进行排序,在最坏的情况下所需得到比较次数是n*(n-1)/2,在最好情况下所需的比较次数是n-1.

算法效率分析

2.折半插入排序

思想:结合了折半查找,利用折半查找的思想进行先找到插入的位置,再移动元素。

折半排序仅减少了比较元素的次数,即ASL,该比较次数与待排序表的初始状态无关,仅取决于表中的元素个数n;而元素的移动次数并未改变,它依旧依赖于待排序表的初始状态。因此,折半插入排序的时间复杂度仍为 0()。但折半插入排序对于数据量不大的排序表能表现出很好的性能,也是一种稳定的排序方法。

代码

可以直接复习折半查找。 

3.希尔排序

注:相对于前面,这个比较常见,也考过,要多回顾。

希尔排序的思想是:先将整个待排记录序列分割成为若干子序列分别进行直接插入排序,待整个序列中的记录“基本有序”时,再对全体记录进行一次直接插入排序。

考题:希尔排序的组内排序采用的是直接插入排序

代码:

思考方向

也可以增量为n/3+1,然后为(n/3+1)/3+1...最后为1。不写成n/3是为了避免最后出现n=2使增量直接为零,而直接错过了增量为1这个最关键的步骤。所以无论你选择什么增量序列,都要保证最后一个增量为1.

那到底我们选择增量序列为多少呢?目前最常见的增量序列,也就是上述代码所使用的希尔增量,它的最坏时间复杂度为0()。其他增量序列目前由于涉及到数学上未解决的难题,并未被完全证实,只是局部结论。所以希尔排序的时间复杂度(默认都是最坏时间复杂度)根据排序所用到的增量序列不同而不同。下表为使用不同的步长序列时希尔排序相应的时间复杂度:

算法分析

我们知道一次直接插入排序是稳定的,但是在不同的插入排序过程中,相同的记录可能在各自的子序列中移动,最后稳定性就会被打乱,所以希尔排序是不稳定排序。

按复杂度分析希尔排序属于改进算法。

希尔排序按按不同视角被分到:

  • 不稳定排序
  • 改进排序
  • 内排序
  • 插入排序

检测:看自己能不能第一眼就看出这个图的意思。

希尔排序的时间性能优于直接插入排序的原因:
①当文件初态基本有序时直接插入排序所需的比较和移动次数均较少。直接插入排序胜。
②当n值较小时,n和的差别也较小,即直接插入排序的最好时间复杂度O(n)和最坏时间复杂度0( )差别不大。直接插入排序也差不多。
③在希尔排序开始时增量较大,分组较多,每组的记录数目少,故各组内直接插入较快,后来增量D逐渐缩小,分组数逐渐减少,而各组的记录数目逐渐增多,但由于已经按D作为距离排过序,使文件较接近于有序状态,所以新的一趟排序过程也较快。
第③点才是最重要的,因此,希尔排序在效率上较直接插入排序有较大的改进。

直接插入排序的最好时间复杂度为0(n),希尔排序排序的最好时间复杂度为O(nlogn),但是希尔排序更有可能靠近这个最好的情况,所以说希尔排序算法的发明,我们终于突破了慢速排序的时代。

 4.比较

  • 8
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值