插入排序

简单 含交互动画

学完这道你应该能: 说清它为什么用「插入」,而不是死记步骤; 合上页面,自己默写出核心代码; 用 30 秒把思路讲清楚。

AI 私教 · 就着本题动画讲
卡住了不用硬扛,按 8 步把这题真正走通。
从读题、试解、找法到手写代码,边问边打勾,适合第一次系统学算法的同学。

题目描述

把数组左边看作"已排序"。每次取右边第一个未排序的数,从右往左找到它该在的位置插入。

输入 = [5, 2, 4, 1, 3]
输出 = [1, 2, 3, 4, 5]

思路解析

为什么不像选择排序那样扫全局?因为左边已经有序了,新牌只要和左边从右往左挨个比,遇到第一个不比它大的就停——逆序时最慢要比到头(O(n²)),但近乎有序时几乎一比就停(O(n))。

每插入完第 i 个数,前缀 0..i 一定有序。插入靠的是"把左边比它大的整体右移一格腾出空位",而不是交换——右移比交换省一次赋值,还保持稳定。

5 是已排序起点:先把第一个数 5 看作已排序区(绿色)。从下标 1 的 2 开始往左插。

插 2 · 比 5 小 → 5 右移:取出 cur=2 暂存(下标 1 这格视作空位)。和左边 5 比:5 大于 2,把 5 右移一格盖到下标 1,继续往左。

插 2 · 左边到头 → 落位:j 已经越过最左端(j=-1),没有更多牌可比,把 cur=2 放进下标 0。前缀变成 [2,5] 有序。

插 4 · 比 5 小 → 5 右移:取出 cur=4。和左边 5 比:5 大于 4,5 右移到下标 2,j 退到下标 1。

插 4 · 遇到 2 不大 → 停:再和 2 比:2 不大于 4,循环停下——这就是关键负例分支,内层不再右移。把 cur=4 落到 2 右边那个空位。前缀 [2,4,5]

插 1 · 比 5 小 → 5 右移:取出 cur=1。它比左边 5 小,5 右移到下标 3。

插 1 · 4 也大 → 再右移:继续往左:4 也大于 1,4 右移到下标 2。可见逆序时要连着右移好几格,这正是插入排序最坏 O(n²) 的来源。

插 1 · 2 也大 → 移到最前:2 也大于 1,再右移;j 越过最左端,cur=1 落到下标 0。前缀 [1,2,4,5]

插 3 · 5、4 右移,遇 2 停:取出 cur=3:5 右移、4 右移,比到 2 时 2 不大于 3,停下,3 落进 2 和 4 之间。整个数组 [1,2,3,4,5] 有序。

插入排序"自适应"——越接近有序越快,这是它相比选择排序的独特优势(选择排序无论如何都跑满 n²/2)。很多库的排序在小区间正是用它收尾。

参考代码(Python)

Python
1for i in range(1, len(nums)):
2    cur = nums[i]                      # 取出待插入的牌,腾出空位
3    j = i - 1                          # 从前缀最右开始往左找
4    while j >= 0 and nums[j] > cur:    # 比 cur 大的整体右移
5        nums[j + 1] = nums[j]          # 右移一格(不是交换)
6        j -= 1
7    nums[j + 1] = cur                  # 遇到不比它大的,落位

复杂度分析

  • 时间复杂度:O(n²) —— 最坏(完全逆序)每个数都要移到头;近乎有序时退化到 O(n)
  • 空间复杂度:O(1) —— 只在原数组上右移,不开额外数组

套路模板

记住骨架:取当前数、左边大的右移、腾出位置落下。希尔排序就是"分组的插入排序",把速度提到亚平方级。

Python
1for i in range(1, n):
2    cur, j = a[i], i - 1
3    while j >= 0 and a[j] > cur:        # 大的右移腾位
4        a[j + 1] = a[j]; j -= 1
5    a[j + 1] = cur                      # 落位

易错点

  • 错误写法:while a[j] > cur:(漏了 j 越界判断)正确写法:while j >= 0 and a[j] > cur:(插到最前时 j 会一路减到 -1,先判 j >= 0 才不会数组越界;and 短路让越界判断在前)
  • 错误写法:用边比边交换(三次赋值)正确写法:只右移、循环结束后落位一次(右移每步只一次赋值比交换省,且相等不动保证稳定)

以上文字与上方动画完全同一思路:先看动画建立直觉 → 读文字巩固 → 关掉页面自己默写一遍代码,能写出来才算真的掌握

下一题 →快速排序 ← 返回题库