Arrays.sort和Collection.sort的實現原理

最近不斷加深對java8之後的Collection方法,發現collection方法中的sort()方法,java的Arrays類中也有靜態sort()方法,同時List類中也有sort方法,而以上的方法都是對數組進行排序處理的,都是非常好用。只是他們之間的參數都是有好幾種。

而深入源碼看看,事實上Collections.sort()方法底層就是調用array.sort()方法。我們跟蹤它的源碼看看:

Collections類中的sort方法:

public static <T extends Comparable<? super T>> void sort(List<T> list) {

    list.sort(null);

}

我們會發現collections.sort()方法調用的是list的sort方法。

default void sort(Comparator<? super E> c) {

    Object[] a = this.toArray();

    Arrays.sort(a, (Comparator) c);

    ListIterator<E> i = this.listIterator();

    for (Object e : a) {

        i.next();

        i.set((E) e);

    }

}

我們接着跟蹤之後就會發現,list裏面是有個sort方法的並且實現了它的,咦?可是list是一個接口呀,怎麼會有默認實現方法體在裏面的呢?這是就是jdk8之後的新特性了,就是接口中也是允許有默認方法了,這個不瞭解的小夥伴們可以自己百度學習一下了。而在jdk8之前,這個list中的sort方法調用的就是ArrayList方法中的sort方法。而我們發現裏面還調用了Arrays.sort(a, (Comparator) c) 通過所謂的雙軸快排的算法;我們接着深入源碼看看:

public static <T> void sort(T[] a, Comparator<? super T> c) {

    if (c == null) {

        sort(a);

    } else {

        if (LegacyMergeSort.userRequested)

            legacyMergeSort(a, c);

        else

            TimSort.sort(a, 0, a.length, c, null, 0, 0);

    }

}

如果我們沒有傳入比較器, LegacyMergeSort.userRequested這個bool值是什麼呢?我們繼續深入源碼看到LegacyMergeSort類中的userRequested,不過這方法將會刪除在未來的版本

/**

* Old merge sort implementation can be selected (for

* compatibility with broken comparators) using a system property.

* Cannot be a static boolean in the enclosing class due to

* circular dependencies. To be removed in a future release.

*/

static final class LegacyMergeSort {

    private static final boolean userRequested =

    java.security.AccessController.doPrivileged(

        new sun.security.action.GetBooleanAction(

            "java.util.Arrays.useLegacyMergeSort")).booleanValue();

}

當我們傳入比較器的時候就會調用TimSort.sort(a, 0, a.length, c, null, 0, 0);

 

總結

不論是Collections.sort方法或者是Arrays.sort方法,底層實現都是TimSort實現的,這是jdk1.7新增的,以前是歸併排序。TimSort算法就是找到已經排好序數據的子序列,然後對剩餘部分排序,然後合併起來. 同時Java1.8的快排是一種雙軸快排,顧名思義:雙軸快排是基於兩個軸來進行比較,跟普通的選擇一個點來作爲軸點的快排是有很大的區別的,雙軸排序利用了區間相鄰的特性,對原本的快排進行了效率上的提高。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章