数据结构学习笔记(14)---插入排序

基本思想:在一个已经排好序的记录子集的基础上,每一步将下一个人等待排序的记录有序插入到已经排序的记录子集上,知道所有待排序记录全部插入为止。
(1)直接插入排序:直接插入排序其实很简单,从第二个元素开始,逐步插入到已排序子序列中。其比较实用与排序记录数比较少的情况,排序数目较大时,该算法排序性能不太好。代码如下:
void InsertSort(int a[], int length)
{
    for (size_t i = 2; i < length; i++)
    {
        a[0] = a[i];
        int j = i - 1;
        while (a[j] > a[0] )
        {
            a[j + 1] = a[j];
            j--;
        }
        a[j+1] = a[0];
    }
}

性能分析:时间复杂度: T(n) = O(n^2) 由于只需要一个人辅助空间a[0]所以 空间复杂度为:S(n) = O(1)

(2)折半插入排序:其实稍微改进了直接插入排序的性能,在寻找插入位置的时候使用折半查找。即直接插入排序的改进版。
void BinSort(int a[], int length)
{
    for (size_t i = 2; i < length; i++)
    {
        a[0] = a[i];
        int low = 1, high = i - 1;
        while (low <= high)
        {
            int mid = (high +low) / 2;
            if (a[mid] < a[0])
            {
                low = mid + 1;
            }
            else
            {
                high = mid - 1;
            }
        }
        for (size_t j = i-1; j >= low; j--)
        {
            a[j + 1] = a[j];
        }
        a[low] = a[0];
    }
}

性能分析:虽然改进了查找的次数,但是并未改变移动元素的时间耗费,所以,折半插入排序的时间复杂度: T(n) = O(n^2) 由于只需要一个人辅助空间a[0]所以 空间复杂度为:S(n) = O(1)

(3)希尔排序:希尔排序其实就是克服了直接插入排序的缺点—对于较大数量的排序记录仍然效率较好。

算法思想:
(a) 选定记录间的距离为d1在整个待排序记录序列中将所有间隔为d1的记录分成一组,进行组内直接插入排序。
(b) 取记录间的距离为d2(d2小于d1)在整个待排序记录序列中,将所有间隔为 d2的记录分成一组,进行组内直接插入排序。
(c)重复步骤2,直至记录间的距离d=1,此时整个只有一个子序列,对该序列进行直接插入排序,完成整个排序过程。

void ShellInsert(int a[], int length, int delta)
{
    size_t j;
    for (size_t i = 1 + delta; i < length; i++)
    {
        if (a[i] < a[i - delta])//0,18,5,60,43,54,90,46
        {
            a[0] = a[i];
            for (j = i - delta; j > 0 && a[j] > a[0]; j-=delta )
            {
                a[j + delta] = a[j];
            }
            a[j + delta] = a[0];
        }
    }
}
void ShellSort(int a[], int length,int delta[],int n)
{
    for (size_t i = 0; i < n; i++)
    {
        ShellInsert(a, length, delta[i]);//进行每一趟
    }
}

性能分析:时间复杂度: T(n) = O(n^1.5) 由于只需要一个人辅助空间a[0]所以 空间复杂度为:S(n) = O(1)

(4)小结 :
排序算法时间复杂度最好情况最坏情况空间复杂度是否稳定
直接插入排序O(n^2)O(n)O(n^2)S(1稳定
折半插入排序O(n^2)O(nlog2(n))O(n^2)S(1)稳定
希尔排序O(n^1.5)S(1)不稳定
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值