归并排序

本文参考

主要思想:将集合不断拆分,排序并合并的过程

时间复杂度稳定O(NlogN)

imgimg

package com.jason.sort;

/**
 * @program: LeetCode
 * @description: 归并排序
 * @author: CodeDuck
 * @create: 2020-07-17 17:25
 **/
public class MergeSort {

    public static void main(String[] args) {
        Integer[] arr = {11, 7, 18, 3, 5, 4, 10, 9};
        mergeSort(arr);
        for (Integer a : arr) {
            System.out.println(a);
        }
    }


    // 类型 T 必须实现 Comparable 接口,并且这个接口的类型是 T 或 T 的任一父类,T 的实例和它的父类的实例之间,可以相互比较大小
    public static <T extends Comparable<? super T>> void mergeSort(T[] arr) {

        // 在排序前,先建好一个长度等于原数组长度的临时数组,避免递归中频繁开辟空间
        T[] tmpArr = (T[]) new Comparable[arr.length];

        mergeSort(arr, tmpArr, 0, arr.length - 1);
    }

    // 实现 拆分操作(从左至右进行拆分)
    private static <T extends Comparable<? super T>> void mergeSort(T[] arr, T[] tmpArr, int left, int right) {

        if (left < right) {
            int mid = (left + right) / 2;
            mergeSort(arr, tmpArr, left, mid);          // 左边归并排序,使得左子序列有序
            mergeSort(arr, tmpArr, mid + 1, right);  	// 右边归并排序,使得右子序列有序
            merge(arr, tmpArr, left, mid, right);       // 将两个有序子数组合并操作
        }
    }

    private static <T extends Comparable<? super T>> void merge(T[] arr, T[] tmpArr, int left, int mid, int right) {

        int i = left;    // 左序列指针
        int j = mid + 1; // 右序列指针
        int t = 0;       // 临时数组指针

        while (i <= mid && j <= right) {
            if (arr[i].compareTo(arr[j]) <= 0) {
                tmpArr[t++] = arr[i++];
            } else {
                tmpArr[t++] = arr[j++];
            }
        }
        while (i <= mid) { // 将左边剩余元素填充进tmpArr中
            tmpArr[t++] = arr[i++];
        }
        while (j <= right) { // 将右序列剩余元素填充进tmpArr中
            tmpArr[t++] = arr[j++];
        }

        t = 0;
        
        // 将tmpArr中的元素全部拷贝到原数组中
        while (left <= right) {
            arr[left++] = tmpArr[t++];
        }
    }
}

快速排序

原文地址:https://www.cnblogs.com/code-duck/p/13469322.html