一文详解归并排序

参考大神的文章,提出自己思路:建议先看大神文章后,再学习本文

「排序算法」归并排序 - 力扣(LeetCode)

由于归并排序还是采用了递归,因此还需要把握递归的三要素。

  • 结束条件
  • 参数列表
  • 返回值

结合本题如下:

归并排序体现了 “分而治之” 的算法思想,具体为:

  • 「分」: 不断将数组从 中点位置 划分开,将原数组的排序问题转化为子数组的排序问题;
  • 「治」: 划分到子数组长度为 1 时,开始向上合并,不断将 左右两个较短排序数组 合并为 一个较长排序数组,直至合并至原数组时完成排序;

【图】

一文详解归并排序_第1张图片

详细步骤

【第一步】

  • 先判断参数列表,数组,起始位置,结束为止。
  • 返回值为空
public static void mergeSorted(int[] q, int l, int r) {

}
  • 「排序算法」归并排序 - 力扣(LeetCode)根据下图分析,当元素被分为只有一个时候,递归结束。因此结束条件为

if (l >= r) {return;}

 【第二步】找到中心点,递归

int mid = l + ((r - l) >> 1);
// 左边分
 mergeSorted(q, l, mid);
// 右边分
mergeSorted(q, mid + 1, r);

【第三步】合并--最难点。

如图所示,到了分的最下层,例如 7 和 3被分为两个数组,

  • 首先我们定义一个i指针,指向7;定义一个j指针指向3,然后对比大小,将其排序存入中间数组。
  • 其次将剩下的元素存入中间数组。
  • 最后将中间数组交给递归的入参数组,完成治的部分。
        // 治
        int k = 0;
        int i = l;
        int j = mid + 1;
        int[] temp = new int[q.length];

        // 填充元素
        while (i <= mid && j <= r) {
            if (q[i] <= q[j]) {
                temp[k++] = q[i++];
            } else {
                temp[k++] = q[j++];
            }
        }
        // 填充剩余的元素
        while (i <= mid) temp[k++] = q[i++];

        while (j <= r) temp[k++] = q[j++];

        //将temp 给递归数组q
        for (i = l, j = 0; i <= r; i++, j++) {
            q[i] = temp[j];
        }

【完整代码】 

package hash;

import java.util.Arrays;

public class MergeSort {
    public static void main(String[] args) {
        int[] q = {7, 3, 2, 6, 0, 1, 5, 4};
        mergeSorted(q, 0, q.length - 1);
        System.out.println("q = " + Arrays.toString(q));

    }

    public static void mergeSorted(int[] q, int l, int r) {
        if (l >= r) {
            return;
        }
        int mid = l + ((r - l) >> 1);
        // 左边分
        mergeSorted(q, l, mid);
        // 右边分
        mergeSorted(q, mid + 1, r);


        // 治
        int k = 0;
        int i = l;
        int j = mid + 1;
        int[] temp = new int[q.length];

        // 填充1
        while (i <= mid && j <= r) {
            if (q[i] <= q[j]) {
                temp[k++] = q[i++];
            } else {
                temp[k++] = q[j++];
            }
        }
        // 填充剩余的
        while (i <= mid) temp[k++] = q[i++];

        while (j <= r) temp[k++] = q[j++];

        //将temp 给q
        for (i = l, j = 0; i <= r; i++, j++) {
            q[i] = temp[j];
        }
    }
}

你可能感兴趣的:(算法,算法,java,c++)