由Collections.sort(list, Comparator()); 说开来

本文详细剖析了Java中Collections.sort()方法的工作原理,包括其如何将List转换为Array进行排序,以及采用的归并排序算法的具体实现细节。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

今天在看相关代码时候看到了 Collections.sort(), 知道Collections是一个工具类 里面包含了很多排序查找等静态方法 是一个很好的util工具类。 但是代码没有仔仔细细的好好看看,今天看了一下 有点小体会。

 

 

首先,开始原始的方法:

 

public static <T> void sort(List<T> list, Comparator<? super T> c) {
	Object[] a = list.toArray();
	Arrays.sort(a, (Comparator)c);
	ListIterator i = list.listIterator();
	for (int j=0; j<a.length; j++) {
	    i.next();
	    i.set(a[j]);
	}
    }
 

发现先将list变成Array,然后再排序,最后再转换回去。

 

 

先说toArray()方法吧

下面分别是ArrayList和LinkedList的实现

 public Object[] toArray() {
        return Arrays.copyOf(elementData, size); //elementData是真正存放东西的数组  size是这个list的长度
 }//不难理解 ArrayList底层就是Array  
 

 

public Object[] toArray() {
	Object[] result = new Object[size];
        int i = 0;
        for (Entry<E> e = header.next; e != header; e = e.next)
            result[i++] = e.element;
	return result;
    }//也不难理解 无非就是便利一下 放到数组里并返回

 

看完了toArray()  再来看一下 sort()吧

 

Array.sort()是这样的

 

public static <T> void sort(T[] a, Comparator<? super T> c) {
	T[] aux = (T[])a.clone();
        if (c==null)
            mergeSort(aux, a, 0, a.length, 0);
        else
            mergeSort(aux, a, 0, a.length, 0, c);
    }

    用的是mergeSort方法 这个方法的几个参数的含义是:src, dest, low, high, offset, compartor 见名之意

 

 

至于这个mergeSort方法嘛 肯定是一个递归操作了 但是这里面也有几个小细节

 

private static void mergeSort(Object[] src,
				  Object[] dest,
				  int low, int high, int off,
				  Comparator c) {
	int length = high - low;            



	// Insertion sort on smallest arrays 这里
        //    INSERTIONSORT_THRESHOLD是7  





意思如果太小 用插入排序会更好




         if (length < INSERTIONSORT_THRESHOLD) {
	    for (int i=low; i<high; i++)
		for (int j=i; j>low && c.compare(dest[j-1], dest[j])>0; j--)
		    swap(dest, j, j-1);
	    return;
	}

        // Recursively sort halves of dest into src
        int destLow  = low;
        int destHigh = high;
        low  += off;
        high += off;
        int mid = (low + high) >>> 1; //注意 这里 没用'/2' 
        mergeSort(dest, src, low, mid, -off, c);
        mergeSort(dest, src, mid, high, -off, c);

        // If list is already sorted, just copy from src to dest.  This is an
        // optimization that results in faster sorts for nearly ordered lists.
        if (c.compare(src[mid-1], src[mid]) <= 0) { //考虑到已经有序的情况






           System.arraycopy(src, low, dest, destLow, length);
           return;
        }

        // Merge sorted halves (now in src) into dest    合并过程






        for(int i = destLow, p = low, q = mid; i < destHigh; i++) {
            if (q >= high || p < mid && c.compare(src[p], src[q]) <= 0)
                dest[i] = src[p++];
            else
                dest[i] = src[q++];
        }
    }
 

上面的一个方法 考虑到了差不多3种情况吧 真正的源码 果然严谨

 

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值