排序——插入排序

简介: 排序——插入排序

插入排序

基本思想

  • 每步将一个待排序的对象,按其关键码大小,插入到前面已经排好序的一组对象的适当位置上,直到对象全部插入为止。
即边插入边排序,保证子序列中随时都是排好序的

基本步骤:

  1. 在R[1..i-1]中查找R[i]的插入位置;
    R[1..j].key <= R[i].key < R[j+1..i-1].key
  2. 将R[j+1..i-1]中的所有记录均后移一个位置;
  3. 将R[i] 插入(复制)到R[j+1]的位置上。

直接插入排序(基于顺序查找)

排序过程:整个排序过程为 n-1趟插入,即先将序列中 第1个记录看成是一个有序子序列,然后从 第2个记录开始, 逐个进行插入,直至整个序列有序。

在这里插入图片描述

算法描述

  • 从R[i-1]向前进行顺序查找,监视哨设置在R[0]
  • 关键字大于R[i].key的记录向后移动
    if( L.r[i].key<L.r[i-1].key){

    R[0] = R[i]; // 设置“哨兵” 
    R[i] = R[i-1];

    for (j=i-2; R[0].key<R[j].key; --j)

    R[j+1] = R[j];
  • 循环结束表明R[i]的插入位置为 j+1
    L.r[j+1]=L.r[0]; //插入到正确位置

算法实现

void InsertSort(SqList &L){
    int i, j;
    for(i = 2; i <= L.length; ++i){
        if(L.r[i].key < L.r[i - 1].key){
            // 将L.r[i]插入有序子表
            L.r[0] = L.r[i];  // 复制为哨兵
            L.r[i] = L.r[i - 1];
            for(j = i - 2; L.r[0].key < L.r[j].key; --j)
                L.r[j + 1] = L.r[j];  // 记录后移
            L.r[i + 1] = L.r[0];  // 插入到正确位置
        }
    }
}

算法分析

时间复杂度 —— O(n^2)

  • 最好的情况(关键字正序)

    • 比较次数:在这里插入图片描述
    • 移动次数:在这里插入图片描述
  • 最坏情况下(关键字逆序)

    • 第 i 趟比较i次,移动i+1次
    • 比较次数:在这里插入图片描述
    • 移动次数:在这里插入图片描述
平均时间复杂度: O(n^2)

空间复杂度 —— O(1)

  • 需要一个记录的辅助空间r(0)

稳定性

  • 稳定
特点:简单、容易实现, 适用于待排序记录基本有序或待排序记录较小时

折半插入排序(基于折半查找)

基本思想:因为 R[1..i-1] 是一个按关键字有序的有序序列,则可以 利用折半查找实现“在R[1..i-1]中查找R[i]的插入位置”,如此实现的插入排序为 折半插入排序。

算法实现

void BiInsertionSort(SqList &L){
    for(i = 2; i <= L.length; ++i){
        L.r[0] = L.r[i];  // 将L.r[i] 暂存到 r[0]
        // 在 L.r[1..i-1]中折半查找插入位置
        low = 1;
        high = i - 1;
        while(low <= high){
            m = (low + high) / 2;  // 折半
            if(L.r[0].key < L.r[m].key)
                high = m - 1;  // 插入点在低半区
            else low = m + 1;  // 插入点在高半区
        }
        for(j = i - 1; j >= high + 1; --j)
            L.r[j + 1] = L.r[j];
        L.r[high + 1] = L.r[0];
    }
}

算法分析

  • 时间复杂度为 O(n^2)

    • 最佳情况下总时间代价为O(nlog2n)
    • 最差和平均情况下仍为O(n^2)
  • 空间复杂度为 O(1)
  • 是一种稳定的排序方法
目录
相关文章
|
6月前
|
搜索推荐 算法 Shell
排序——插入排序
排序——插入排序
42 0
|
6月前
|
算法 搜索推荐
排序——选择排序
排序——选择排序
55 0
|
存储 搜索推荐 测试技术
排序篇(一)----插入排序
排序篇(一)----插入排序
46 0
|
算法 搜索推荐 索引
排序篇(二)----选择排序
排序篇(二)----选择排序
31 0
|
存储 搜索推荐 测试技术
排序(1)之插入排序
从今天小编就开始给大家介绍排序的内容,对于排序内容我们一共分,插入,选择,交换,归并这几个大类,那么今天小编给大家带来的就是插入排序
97 0
|
搜索推荐
排序(2)之选择排序
继插入排序后,今天小编就给大家另一个模块,选择排序的学习,那么话不多说,我们直接进入正题。
114 0
|
存储 算法 搜索推荐
排序(4)——归并排序
今天给大家带来比较排序的最后一种,归并排序,这个排序,需要我们对递归,循环控制要有着较强的理解,我相信大家通过前面和小编的一起学习,这里肯定也是得心应手。
95 0
|
索引
掌握常见的几种排序-选择排序
选择排序是一种简单的排序,时间复杂度是O(n^2),在未排序的数组中找到最小的那个数字,然后将其放到起始位置,从剩下未排序的数据中继续寻找最小的元素,将其放到已排序的末尾,以此类推,直到所有元素排序结束为止。
116 0
掌握常见的几种排序-选择排序
|
算法 Shell
排序——希尔排序
排序——希尔排序
121 0
排序——希尔排序
|
算法
排序——直接插入排序
排序——直接插入排序
111 0
排序——直接插入排序