# 归并排序 * **介绍** * `归并特性` * 一个列表两段有序,通过归并实现合并成一段有序列表。 * 复杂度O(n log(n)) * 思路:先分解在合并 * 过程: * 分解:将列表越分越小,直至分成一个元素; * 终止条件:一个元素是有序的; * 合并:将两个有序列表归并,列表越来越大。 * 关键字: * 分解 * 归并 * 存在问题 * 需要额外的内存开销 * 快速排序 `>` 归并排序 `>` 堆排序 * **原理** * 通过对若干个有序结点序列的归并来实现排序。 * 所谓归并是指将若干个已排好序的部分合并成一个有序的部分。 * **代码** ```go /** MergeSort 实现归并排序(前提列表有序) 包含:分解 + 合并 */ func MergeSort(li []int, low, high int) { if low < high { mid := (low + high) / 2 MergeSort(li, low, mid) MergeSort(li, mid + 1, high) Merge(li, low, mid, high) } } /** Merge 归并 */ func Merge(li []int, low, mid, high int) { i, j, lt, t := low, mid + 1, make([]int, len(li)), 0 for i <= mid && j <= high { // 将结果拼接到新的数组 if li[i] < li[j] { lt[t], i, t = li[i], i + 1, t + 1 } else { lt[t], j, t = li[j], j + 1, t + 1 } } for i <= mid { lt[t], i, t = li[i], i + 1, t + 1 } for j <= high { lt[t], j, t = li[j], j + 1, t + 1 } for i, j := low, 0 ; i <= high; i, j = i + 1, j + 1 { // 因为存在递归,将数值填回数组 li[i] = lt[j] } } ``` * **过程** ![并归排序](.\img\归并排序.gif)