Java 排序算法详解:冒泡排序、选择排序、堆排序

在学习算法的过程中,排序是非常重要的一部分,它不仅是面试常考题,也是理解算法思路和复杂度分析的基础。今天,我们来讲三种经典排序算法:冒泡排序、选择排序、堆排序,并附上可运行的 Java 示例。

冒泡排序(Bubble Sort)

概念

冒泡排序是一种交换排序,通过重复比较相邻元素,将较大的元素慢慢"冒泡"到数组的末尾。
特点

时间复杂度:O(n²)

空间复杂度:O(1)

稳定排序(相等元素相对位置不变)
思路

从数组的第一个元素开始,依次比较相邻两个元素,如果前一个比后一个大,则交换。

每一轮循环后,最大的元素会被放到最后。

重复步骤 1 和 2,直到所有元素有序。

java 复制代码
public class BubbleSortDemo {
    public static void bubbleSort(int[] arr) {
        int n = arr.length;
        for (int i = 0; i < n - 1; i++) {
            boolean swapped = false; // 优化:如果一轮没有交换,则提前结束
            for (int j = 0; j < n - 1 - i; j++) {
                if (arr[j] > arr[j + 1]) {
                    int temp = arr[j];
                    arr[j] = arr[j + 1];
                    arr[j + 1] = temp;
                    swapped = true;
                }
            }
            if (!swapped) break; // 提前退出
        }
    }

    public static void main(String[] args) {
        int[] arr = {5, 2, 9, 1, 5, 6};
        System.out.println("排序前:" + java.util.Arrays.toString(arr));
        bubbleSort(arr);
        System.out.println("排序后:" + java.util.Arrays.toString(arr));
    }
}

选择排序(Selection Sort)

概念

选择排序是一种选择最小(或最大)元素的排序方法,每次从未排序部分选择最小元素,放到已排序部分的末尾。
特点

时间复杂度:O(n²)

空间复杂度:O(1)

不稳定排序(相等元素可能改变顺序)
思路

从数组中找到最小元素。

将其与当前未排序区的第一个元素交换。

将已排序区的范围加1,重复步骤 1 和 2。

java 复制代码
public class SelectionSortDemo {
    public static void selectionSort(int[] arr) {
        int n = arr.length;
        for (int i = 0; i < n - 1; i++) {
            int minIndex = i;
            for (int j = i + 1; j < n; j++) {
                if (arr[j] < arr[minIndex]) {
                    minIndex = j;
                }
            }
            // 交换
            int temp = arr[i];
            arr[i] = arr[minIndex];
            arr[minIndex] = temp;
        }
    }

    public static void main(String[] args) {
        int[] arr = {64, 25, 12, 22, 11};
        System.out.println("排序前:" + java.util.Arrays.toString(arr));
        selectionSort(arr);
        System.out.println("排序后:" + java.util.Arrays.toString(arr));
    }
}

堆排序(Heap Sort)

概念

堆排序是一种利用堆(Heap)结构的选择排序,通过构建最大堆或者最小堆实现排序。

最大堆:父节点 >= 子节点,适合升序排序

最小堆:父节点 <= 子节点,适合降序排序
特点

时间复杂度:O(n log n)

空间复杂度:O(1)

不稳定排序
思路

构建最大堆。

将堆顶(最大值)与最后一个元素交换,然后对剩余部分重新调整堆。

重复步骤 2,直到所有元素有序。

java 复制代码
public class HeapSortDemo {

    public static void heapSort(int[] arr) {
        int n = arr.length;

        // 构建最大堆
        for (int i = n / 2 - 1; i >= 0; i--) {
            heapify(arr, n, i);
        }

        // 逐个将堆顶元素与末尾元素交换,并重新调整堆
        for (int i = n - 1; i > 0; i--) {
            int temp = arr[0];
            arr[0] = arr[i];
            arr[i] = temp;

            heapify(arr, i, 0); // 调整剩余部分
        }
    }

    // 堆化函数
    private static void heapify(int[] arr, int heapSize, int rootIndex) {
        int largest = rootIndex;
        int left = 2 * rootIndex + 1;
        int right = 2 * rootIndex + 2;

        if (left < heapSize && arr[left] > arr[largest]) {
            largest = left;
        }
        if (right < heapSize && arr[right] > arr[largest]) {
            largest = right;
        }
        if (largest != rootIndex) {
            int swap = arr[rootIndex];
            arr[rootIndex] = arr[largest];
            arr[largest] = swap;

            heapify(arr, heapSize, largest);
        }
    }

    public static void main(String[] args) {
        int[] arr = {12, 11, 13, 5, 6, 7};
        System.out.println("排序前:" + java.util.Arrays.toString(arr));
        heapSort(arr);
        System.out.println("排序后:" + java.util.Arrays.toString(arr));
    }
}
相关推荐
全栈陈序员几秒前
【Python】基础语法入门(三十三)—— 日志系统详解:用 logging 记录程序运行
java·开发语言·python
她的男孩9 分钟前
低代码加字段后表结构怎么同步:预览安全 DDL,高风险变更再强制执行
java·spring boot·低代码
简简单单就是我_hehe15 分钟前
一次 ClickHouse 服务器磁盘告警的排查与修复实录
java·服务器·前端
Thomas.Sir20 分钟前
第11课:文件上传下载、跨域CORS配置,SpringBoot4.x跨域新方案
java·spring boot
Figo_Cheung24 分钟前
Figo基于结构空间算法假设(SSAH)的生成式大模型优化范式与工程实现边界研究——提出适应AGI架构演化的自适应拓扑感知表征机制
算法·架构·agi
wuminyu25 分钟前
JVM规范学习总结:class执行性能差异
java·linux·c语言·jvm·c++
一条泥憨鱼36 分钟前
【RabbitMQ】高级篇
java·分布式·rabbitmq·php·ruby
京师20万禁军教头44 分钟前
50-常用类-Arrays
java
寰梦1 小时前
Spring Boot + MinIO 大文件上传完整实战:MD5 秒传、分片上传、断点续传与引用一致性
java·spring boot·文件上传·minio
旖旎夜光1 小时前
LCR 170:交易逆序对的总数(归并排序) —— 题解
c++·学习·算法·leetcode·排序算法