基数排序详解

基数排序详解

思路分析

  1. 基数排序是典型的以空间换时间的排序算法,但是当对大量数据进行排序时,可能会出现空间不足的情况
  2. 基数排序实质上是对桶排序的升级,核心思想是对数组中的每个元素从低位到高位开始排序,在较小数据高位补零,使数组中个元素长度相同
  3. 因此需要大量空间,即创建十个桶用来辅助排序,用二维数组来模拟十个桶,则桶的顺序是实现确定的,将数组中的元素按照某一位的大小依次进行排序,没排序一次,将排好序的结构再存放到原始数组中,然后开始下一轮排序,直到数组元素的最高位也参与过排序
  4. 注意二维数组在创建后默认所有元素都为0,因此在向二维数组即桶中添加元素中,需要一个索引记录当前桶中的元素个数,方便取出,因此还需要一个一维数组
  5. 源码及详解如下

源码及详解

/**
     * 基数排序,桶排序的升级
     *
     * @param arr 要排序的数组
     */
    public static void radixSort(int[] arr) {
        //获取数组中最大元素的位数
        int max = arr[0];
        for (int i = 1; i < arr.length; i++) {
            if (arr[i] > max) {
                max = arr[i];
            }
        }
        int maxLength = (max + "").length();
        //用二维数组模拟10个桶,即二维数组的每一行代表一个桶
        int[][] bucket = new int[10][arr.length];
        //定义数组bucketElementCount保存10个桶中实际存储的元素个数
        int[] bucketElementCount = new int[10];
        //循环处理每一位
        for (int k = 0, n = 1; k < maxLength; k++, n *= 10) {
            //先将数组中的元素放入桶中
            for (int i = 0; i < arr.length; i++) {
                int digitOfElement = arr[i] / n % 10;
                bucket[digitOfElement][bucketElementCount[digitOfElement]] = arr[i];
                bucketElementCount[digitOfElement]++;
            }
            //按照个位数字大小放置完毕后,将桶中的数字取出来放回到原数组arr
            int index = 0;
            //遍历存放实际桶中元素个数的一维数组,如果一维数组中索引对应元素=0,说明对应桶中没有元素,不再遍历,
            for (int i = 0; i < bucketElementCount.length; i++) {
                if (bucketElementCount[i] != 0) {
                    //否则遍历桶中元素,将其元素重新赋值给原始数组
                    for (int j = 0; j < bucketElementCount[i]; j++) {
                        arr[index] = bucket[i][j];
                        index++;
                    }
                }
                //将保存实际桶中元素个数的数字清0
                bucketElementCount[i] = 0;
            }
        }
    }
posted @ 2021-06-03 16:48  mx_info  阅读(173)  评论(0)    收藏  举报