希尔排序详解

希尔排序是插入排序的一种更高效的改进版本,也称为"缩小增量排序"


前言

希尔排序的核心思想是:使数组中任意间隔为 gap 的元素都是有序的。这样的数组被称为是 gap 有序 的,基本思路:先将整个待排序的序列分割成若干个子序列,分别进行直接插入排序。待整个序列中的记录"基本有序"时,再对全体记录进行一次直接插入排序,如何分割? 通过一个增量序列(Gap Sequence) 来控制。增量逐渐减小,最终减至 1(即对整个数组进行最后一次标准的插入排序)

**我们以数组 [8, 9, 1, 7, 2, 3, 5, 4, 6, 0] 为例,详细演示希尔排序的每一步过程,**数组长度 n = 10,使用希尔增量序列:gap = 5 → 2 → 1

排序后数组: [3, 5, 1, 6, 0, 8, 9, 4, 7, 2]

第2轮:gap = 2

排序后数组: [0, 2, 1, 4, 3, 5, 7, 6, 9, 8]

第3轮:gap = 1

对整个数组进行标准插入排序:数组:[0, 2, 1, 4, 3, 5, 7, 6, 9, 8]

最终排序结果: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

实现希尔排序

cpp 复制代码
void shellSort(int arr[], int n) {
   int gap=n/2;
     while (gap > 0) {
        for (int i = gap; i < n; i++) {
            int temp = arr[i];
            int j = i - gap;  // 从前一个位置开始
            
            while (j >= 0 && arr[j] > temp) {
                arr[j + gap] = arr[j];  // 向后移动
                j -= gap;
            }
            arr[j + gap] = temp;  // 插入到正确位置
        }
        gap /= 2;
    }
}
cpp 复制代码
初始数组: 8 9 1 7 2 3 5 4 6 0 
=== 第1轮排序,gap = 5 ===
处理元素 arr[5] = 3: 8 9 1 7 2 [3] 5 4 6 0 
  移动 arr[0](8) -> arr[5]
  插入 3 到位置 0
  当前数组: 3 9 1 7 2 8 5 4 6 0 
处理元素 arr[6] = 5: 3 9 1 7 2 8 [5] 4 6 0 
  移动 arr[1](9) -> arr[6]
  插入 5 到位置 1
  当前数组: 3 5 1 7 2 8 9 4 6 0 
处理元素 arr[7] = 4: 3 5 1 7 2 8 9 [4] 6 0 
  移动 arr[2](1) -> arr[7]
  插入 4 到位置 2
  当前数组: 3 5 4 7 2 8 9 1 6 0 
处理元素 arr[8] = 6: 3 5 4 7 2 8 9 1 [6] 0 
  移动 arr[3](7) -> arr[8]
  插入 6 到位置 3
  当前数组: 3 5 4 6 2 8 9 1 7 0 
处理元素 arr[9] = 0: 3 5 4 6 2 8 9 1 7 [0] 
  移动 arr[4](2) -> arr[9]
  插入 0 到位置 4
  当前数组: 3 5 4 6 0 8 9 1 7 2 
本轮排序后: 3 5 4 6 0 8 9 1 7 2 

=== 第2轮排序,gap = 2 ===

=== 第3轮排序,gap = 1 ===

最终排序结果: 0 1 2 3 4 5 6 7 8 9 

总结

希尔排序通过将大规模数组先调整为"基本有序"的状态,极大地减少了最后一次插入排序的比较和移动次数,从而提升了整体性能。它是一种非常巧妙的算法,虽然在实际应用中已被更高效的算法所取代,但其思想仍然非常值得学习和借鉴。它很好地展示了如何通过预处理来优化一个简单算法

相关推荐
天天爱吃肉82181 分钟前
【跨界封神|周杰伦×王传福(陶晶莹主持):音乐创作与新能源NVH测试,底层逻辑竟完全同源!(新人必看入行指南)】
python·嵌入式硬件·算法·汽车
im_AMBER2 分钟前
Leetcode 114 链表中的下一个更大节点 | 删除排序链表中的重复元素 II
算法·leetcode
xhbaitxl14 分钟前
算法学习day38-动态规划
学习·算法·动态规划
多恩Stone15 分钟前
【3D AICG 系列-6】OmniPart 训练流程梳理
人工智能·pytorch·算法·3d·aigc
历程里程碑17 分钟前
普通数组----轮转数组
java·数据结构·c++·算法·spring·leetcode·eclipse
pp起床18 分钟前
贪心算法 | part02
算法·leetcode·贪心算法
sin_hielo18 分钟前
leetcode 1653
数据结构·算法·leetcode
2501_9011478320 分钟前
面试必看:优势洗牌
笔记·学习·算法·面试·职场和发展
李日灐21 分钟前
C++进阶必备:红黑树从 0 到 1: 手撕底层,带你搞懂平衡二叉树的平衡逻辑与黑高检验
开发语言·数据结构·c++·后端·面试·红黑树·自平衡二叉搜索树
熬夜有啥好29 分钟前
数据结构——排序与查找
数据结构