每天学一个算法-- 归并排序(Merge Sort)

📘 归并排序(Merge Sort)


1. 问题定义

给定数组 (A[1...n]),要求输出:

A\[1\]≤A\[2\]≤⋯≤A\[n\]\]\[ A\[1\] \\le A\[2\] \\le \\dots \\le A\[n\] \]\[A\[1\]≤A\[2\]≤⋯≤A\[n\]

2. 核心思想

归并排序同样基于:

分治(Divide and Conquer)

但与快速排序的关键区别:

快排:先划分,再递归(Partition-based)
归并:先递归,再合并(Merge-based)

3. 核心术语

3.1 分治(Divide)

将数组递归拆分为:

A\[l..r\]→A\[l..mid\]+A\[mid+1..r\]\]\[ A\[l..r\] \\rightarrow A\[l..mid\] + A\[mid+1..r\] \]\[A\[l..r\]→A\[l..mid\]+A\[mid+1..r\]

直到每个子数组长度为 1

3.2 合并(Merge)

定义:

将两个已排序数组合并为一个有序数组

关键性质:

  • 输入:两个有序序列
  • 输出:一个有序序列

3.3 稳定性(Stability)

归并排序是:

稳定排序

因为合并时:

  • 相等元素保持原顺序

3.4 非原地(Out-of-place)

归并排序需要:

  • 额外数组辅助合并

空间复杂度为:

O(n)\]\[ O(n) \]\[O(n)

4. 算法结构


4.1 主函数

text 复制代码
MergeSort(A, l, r):
    if l >= r:
        return

    mid = (l + r) // 2

    MergeSort(A, l, mid)
    MergeSort(A, mid+1, r)

    Merge(A, l, mid, r)

4.2 合并函数

text 复制代码
Merge(A, l, mid, r):
    创建临时数组 temp

    i = l
    j = mid + 1

    while i ≤ mid and j ≤ r:
        if A[i] ≤ A[j]:
            temp.append(A[i])
            i++
        else:
            temp.append(A[j])
            j++

    将剩余部分加入 temp

    拷贝回 A[l..r]

5. 核心机制(教学重点)

5.1 归并排序的本质

不是"直接排序",而是:

先拆到最小,再逐层合并

5.2 为什么一定能排序成功?

因为:

每一层都满足:

  • 子数组已经有序
  • 合并操作保持有序

5.3 合并过程本质

本质是:

两个指针的线性扫描

6. 示例

初始数组

text 复制代码
[6, 3, 8, 5]

拆分过程

text 复制代码
[6,3,8,5]
→ [6,3] [8,5]
→ [6] [3] [8] [5]

合并过程

text 复制代码
[6] + [3] → [3,6]
[8] + [5] → [5,8]

最终

text 复制代码
[3,6] + [5,8] → [3,5,6,8]

7. 时间复杂度

7.1 递推式

T(n)=2T(n/2)+O(n)\]\[ T(n) = 2T(n/2) + O(n) \]\[T(n)=2T(n/2)+O(n)

7.2 求解

T(n)=O(nlog⁡n)\]\[ T(n) = O(n \\log n) \]\[T(n)=O(nlogn)

7.3 关键理解

  • 每一层合并成本:(O(n))(O(n))(O(n))
  • 层数:(log⁡n)(\log n)(logn)

8. 空间复杂度

需要辅助数组:

O(n)\]\[ O(n) \]\[O(n)

9. 与快速排序对比(重点)

项目 快速排序 归并排序
核心操作 partition merge
时间复杂度 平均 (n log n) 始终 (n log n)
最坏情况 (n^2) (n log n)
空间 原地 额外 (n)
稳定性

10. 常见错误

❌ 错误1:认为 merge 很复杂

👉 本质只是"双指针"

❌ 错误2:忘记处理剩余部分

必须:

text 复制代码
while i ≤ mid
while j ≤ r

❌ 错误3:边界写错

特别是:

text 复制代码
mid + 1

11. 关键结论

  1. 归并排序核心是 merge
  2. 时间复杂度稳定 (nlogn)(n log n)(nlogn)
  3. 空间换时间
  4. 适用于大规模稳定排序

12. 最小教学总结

归并排序不是"在排",而是:
把问题拆小 → 再把有序结果合起来

相关推荐
算法鑫探1 小时前
算法中的二分法(二分查找)详解及示例
c语言·数据结构·算法·新人首发
叶子野格2 小时前
《C语言学习:编程例题》8
c语言·开发语言·c++·学习·算法·visual studio
澈2072 小时前
排序算法入门:冒泡、选择、插入排序详解
数据结构·算法·排序算法
smj2302_796826522 小时前
解决leetcode第3901题好子序列查询
python·算法·leetcode
_深海凉_2 小时前
LeetCode热题100-每日温度
算法·leetcode·职场和发展
迷你可可小生2 小时前
面经学习(二)
学习·算法
John.Lewis2 小时前
C++加餐课-二叉树:进阶算法
数据结构·c++·算法
郝学胜-神的一滴2 小时前
ReLU激活函数全解析:从原理到实战,解锁深度学习核心激活单元
人工智能·pytorch·python·深度学习·算法
AGV算法笔记2 小时前
最新感知算法论文分析:RaCFormer 如何提升雷达相机 3D 目标检测性能?
数码相机·算法·3d·自动驾驶·机器人视觉·3d目标检测·感知算法