數組排序(5)- 歸併排序

(一)歸併排序算法

    和選擇排序同樣,歸併排序的性能不受輸入數據的影響,但表現比選擇排序好的多,由於始終都是O(n log n)的時間複雜度。代價是須要額外的內存空間。歸併排序是創建在歸併操做上的一種有效的排序算法。該算法是採用分治法(Divide andConquer)的一個很是典型的應用。歸併排序是一種穩定的排序方法。將已有序的子序列合併,獲得徹底有序的序列;即先使每一個子序列有序,再使子序列段間有序。若將兩個有序表合併成一個有序表,稱爲2-路歸併。數組

  1.算法描述app

    (1)把長度爲n的輸入序列分紅兩個長度爲n/2的子序列;ide

    (2)對這兩個子序列分別採用歸併排序;性能

    (3)將兩個排序好的子序列合併成一個最終的排序序列。ui

  2.算法分析spa

  (1)最佳狀況:T(n) = O(nlogn)code

  (2)空間複雜度: O(n)blog

  (3)穩定性: 穩定排序

(二)代碼實現

public class MergeSort {
    public static void main(String[] args) {
        int[] arr = {3,4,1,2,7,8,6,5,9};
        sort(arr);//排序
        System.out.println("-----------------------------------------");
        print(arr);//打印結果
    }

    public static void sort(int[] arr){
        if(arr == null || arr.length <= 1){
            return;
        }
        sort(arr,0,arr.length - 1);
    }

    private static void sort(int[] arr, int left, int right) {
        //邊界條件
        if(left >= right){
            return;
        }
        int middle = (left + right) / 2;
        sort(arr,left,middle); //對左邊序列進行排序
        sort(arr,middle + 1,right); //對右邊序列進行排序
        //將兩個子序列歸併成一個有序序列
        merge(arr,left,middle,right);
        print(arr);
    }

    private static void merge(int[] arr, int left, int middle, int right) {
        //左邊數組[left,middle],右邊數組[middle + 1,right]
        int[] temp = new int[right - left + 1];
        int i = left;
        int j = middle + 1;
        int k = 0;

        while (i <= middle && j <= right){
            if(arr[i] <= arr[j]){//"="符號保證了歸併排序是穩定排序
                temp[k++] = arr[i++];
            }else {
                temp[k++] = arr[j++];
            }
        }
        //左邊數組沒排序完
        while (i <= middle){
            temp[k++] = arr[i++];
        }
        //右邊數組沒排序完
        while (j <= right){
            temp[k++] = arr[j++];
        }

        //將temp數組賦值給原數組
        for (int p = 0; p < temp.length; p++) {
            arr[left + p] = temp[p];
        }
    }

    public static void print(int[] arr){
        StringBuilder sb = new StringBuilder("[");
        for (int i = 0; i < arr.length; i++) {
            sb.append(arr[i]);
            if(i != arr.length - 1){
                sb.append(", ");
            }
        }
        System.out.println(sb.append("]"));
    }
}
MergeSort
相關文章
相關標籤/搜索