排序算法系列之希尔排序

希尔排序

1 基本原理

1 核心思想:希尔排序也是一种插入排序,它是简单插入排序经过改进之后的一个更高效的版本,也称为缩小增量排序。
2 算法分析
希尔排序是把序列按下标的一定增量分组,对每组使用直接插入排序算法排序;随着增量逐渐减少,每组包含的元素越来越多,当增量减至1时,整个序列恰好被分成一组,排序便终止。

2 实例说明

如上图所示,以一组数据{9,1,2,5,7,4,8,6,3,5} 为例,进行直接插入排序的算法演示:
  1. 令步长gap=5,则原数组分为[9,4],[1,8],[2,6],[3,5],[5,7]五个数组,分别进行直接插入排序,数组变为[4,1,2,3,5,9,8,6,5,7]。
  2. 令步长gap=2,则原数组分为[4,2,5,8,5]和[1,3,9,6,7]两个数组,分别进行直接插入排序,数组变为[2,1,4,3,5,6,5,7,8,9]。
  3. 令步长gap=1,对数组进行直接插入排序,完成排序。

3 代码实现

// 希尔排序(C++)
void ShellSort(vector<int> &vi)
{
    int j, gap;
    for (gap = vi.size() / 2; gap>0; gap /= 2)
    {
        for (j = gap; j<vi.size(); j++)
        {
            if (vi[j]<vi[j - gap]) //组内元素进行直接插入排序
            {
                int temp = vi[j];
                int k = j - gap;
                while (k >= 0 && vi[k]>temp)
                {
                    vi[k + gap] = vi[k];
                    k -= gap;
                }
                vi[k + gap] = temp;
            }
        }

        for (auto x : vi)
            cout << x << " ";
        cout << endl;
    }
}

4 性能分析

希尔排序是按照不同步长对元素进行插入排序,当刚开始元素很无序的时候,步长最大,所以插入排序的元素个数很少,速度很快;当元素基本有序了,步长很小,插入排序对于有序的序列效率很高。
希尔排序的时间复杂度与步长取值有关。

  • 1 时间复杂度
    希尔增量时间复杂度为O(n^2),而Hibbard增量的希尔排序的时间复杂度为O( n^1.5 ),希尔排序时间复杂度的下界是O(n*log2n)。
  • 2 空间复杂度
    希尔排序过程中用到了直接插入排序,需要临时变量存储待排序元素,因此空间复杂度为O(1)
  • 3 算法稳定性
    希尔排序是不稳定的算法,对于相同的两个数,可能由于分在不同的组中而导致它们的顺序发生变化。
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值