Arrays.sort底层排序算法解析

一直以来,我都认为Java内部排序的算法是快速排序。直到有一天,我在面经上看到了有一道这样子的问题,我才发觉,事情远没有我想的那么简单。

在JDK1.8中,自带的底层排序算法会根据传入的目标数组大小的不同采取不同的排序方法。

小数组排序

在底层源码中,对小数组采用快速排序。如果数组的长度小于 QUICKSORT_THRESHOLD = 286 时,使用快速排序。

sql 复制代码
// Use Quicksort on small arrays
if (right - left < QUICKSORT_THRESHOLD) {
    sort(a, left, right, true);
    return;
}

微小数组排序

对于更小的数组,采用插入排序。当数组长度小于 INSERTION_SORT_THRESHOLD = 47 时,采用插入排序。

css 复制代码
// Use insertion sort on tiny arrays
if (length < INSERTION_SORT_THRESHOLD) {
    if (leftmost) {
        // Insertion sort on smallest arrays
        for (int i = left, j = i; i < right; j = ++i) {
            int ai = a[i + 1];
            while (ai < a[j]) {
                a[j + 1] = a[j];
                if (j-- == left) {
                    break;
                }
            }
            a[j + 1] = ai;
        }
        return;
    }
}

大数组排序

对于大数组,首先进行一次数组遍历,标记数组的升序和降序的起始位置,然后根据数组的结构选择归并排序或快速排序。如果升序和降序序列的数量超过 MAX_RUN_COUNT = 67,则采用快速排序。否则,采用归并排序。

css 复制代码
/*
 * Index run[i] is the start of i-th run
 * (ascending or descending sequence).
 */
int[] run = new int[MAX_RUN_COUNT + 1];
int count = 0; 
run[0] = left;

// Check if the array is nearly sorted
for (int k = left; k < right; run[count] = k) {
    // Ascending sequence
    if (a[k] < a[k + 1]) {
        while (++k <= right && a[k - 1] <= a[k]);
    } 
    // Descending sequence
    else if (a[k] > a[k + 1]) {
        while (++k <= right && a[k - 1] >= a[k]);
        // Reverse the descending sequence
        for (int lo = run[count] - 1, hi = k; ++lo < --hi; ) {
            int t = a[lo]; 
            a[lo] = a[hi]; 
            a[hi] = t;
        }
    } 
    // Equal elements
    else {
        for (int m = MAX_RUN_LENGTH; ++k <= right && a[k - 1] == a[k]; ) {
            if (--m == 0) {
                sort(a, left, right, true);
                return;
            }
        }
    }

    // Check if array is highly unstructured
    if (++count == MAX_RUN_COUNT) {
        sort(a, left, right, true);
        return;
    }
}

总的来说,Arrays.sort 在底层使用了快速排序、插入排序以及归并排序等算法,通过根据数组的大小和结构来选择合适的排序策略,以达到更好的性能。

相关推荐
头发还在的女程序员18 小时前
医院陪诊管理系统怎么选择?——2026 年选型避坑与架构参考
java·开发语言·陪诊系统·陪诊app·医院陪诊陪护
CodeStats18 小时前
【Spring事务】Spring事务注解 @Transactional 完整体系:从 MySQL 隔离级别到 MyBatis 原理详解
java·spring·mybatis·事务·transactional
我命由我1234519 小时前
Android 开发问题:为 PDFView 设置一个带有黑色边框的背景 drawable,但边框没有生效
android·java·java-ee·android studio·android jetpack·android-studio·android runtime
都叫我大帅哥21 小时前
从Python到Java:为什么企业级Agent最终会选择Java?
java·ai编程
wanderist.21 小时前
Lambda表达式在算法竞赛中的应用
java·开发语言·算法
腻害兔1 天前
【若依项目-产品经理视角】RuoYi-Vue-Pro 源码拆解:IM 即时通讯模块,一个被低估的「全功能聊天系统」
java·前端·vue.js·产品经理·ai编程
心念枕惊1 天前
.NET CORE 授权进阶-角色、策略与动态权限实现
java·前端·.netcore
景同学1 天前
把 AI 用到线上运维:可行、有效,前提是喂足信息——一次 Full GC 排障实录
java·人工智能·后端
C++、Java和Python的菜鸟1 天前
第7章 后端Web实战(Tlias系统)
java
憧憬成为java架构高手的小白1 天前
黑马八股--spring框架学习
java·学习·spring