排序算法学习10_基数排序(Java)

基数排序


学习目标:掌握基数排序算法的原理和思想

一、前提知识

  排序算法概念、时间复杂度。可前往此网址 排序算法学习01_算法基础介绍阅读

二、基数排序介绍

  基数排序( Radix sort ),基数排序算法通过对原序列中元素的各个位数分别进行切割来排序,可以说是我们前两篇计数排序桶排序的结合版本,也是一种非比较型的整数排序算法。且稳定的。

三、基数排序工作原理

  基数排序也如计数排序一样,利用数组下标排序元素,但此时它并不是直接用元素大小来对应数组下标,而是通过对元素值的每个位数进行切割再来对应数组下标放置元素

  那么显然此时一个数组是远远不够的,一个索引位只能放置一个元素,所以基数排序结合了桶排序的设计逻辑这样每个桶(下标)位就可以放置多个元素

  基数排序通过切割整数位数,每次先取整数最后一位根据桶位置先进行放置元素放置完毕依次取出放回原序列,然后依次向前递进一位再放置,重复该逻辑,直到 所有最高位放置完毕 即可得到一个排序好的序列

​ 图解:

四、基数排序设计思路

  基数排序算法设计,较于我们上篇学的前两种排序是比较简单的,只需要得到原序列最大值的长度,就可以得到要排序的次数,然后设计一个公式,每次对值进行入桶时都能根据该公式进入对应的桶

  • 得到最大值长度,我们可以使用JDK内置的String类提供的valueOf方法对数值进行转换成String类型,然后取长度
  • 我们知道,值入桶是根据,值的位数进行的。那么获取每个值的位数相信小伙伴们都学过
    • 首先对个位进行处理,那么如果存在元素123,那获取个位 = 123 / 1 % 10
    • 百位 = 123 / 10 % 10 千位 = 123 / 100 % 10
    • 。。。得到该规律,我们就可以进行实现了
  • 还有,对于桶的选择,依然采用上篇桶排序的思路,用ArrayList
  • 那么接下来看代码吧

五、代码实现

public static void radixSort(int[] arr){
    int max = arr[0]; // 最大值
    for(int i = 1;i < arr.length;i++){
        if(max < arr[i]) max = arr[i];
    }
    int maxLength = String.valueOf(max).length(); // 根据最大值获取长度

    ArrayList<ArrayList<Integer>> bucketList = new ArrayList<>(); // 桶列表
    // 位数取值为0~9,那么创建10个桶即可
    for(int i = 0;i < 10;i++){
        bucketList.add(new ArrayList<>());
    }
    // 排序
    int digit = 1; // 先表示个位
    for(int i = 1;i <= maxLength;i++){
		// 遍历序列入桶
        for(int j = 0;j < arr.length;j++){
            int index = (arr[j] / digit) % 10; // 获取该位数对应的桶位置
            bucketList.get(index).add(arr[j]);
        }
        digit*=10; // 计算前一个位数
        int arrIndex = 0; // 作为序列索引,辅助赋值
        // 遍历桶写回原序列,从第一个桶开始写就是升序,反之
        for(int k = 0;k < 10;k++){
            if(bucketList.get(k).size() > 0) {
                for (int m = 0; m < bucketList.get(k).size(); m++) {
                    arr[arrIndex++] = bucketList.get(k).get(m);
                }
            }
            bucketList.get(k).clear(); // 清空
        }

    }

}

六、时间复杂度

  基数排序是非比较排序算法,算法的时间复杂度是O(n*k). 关于更多详细请参考其他书籍或博客

七、总结

  基数排序在运算性能上可能没有计数桶排序好,但是它也弥补了计数排序和桶排序的不足,计数排序不适合排序元素相差过大的序列,而桶排序不适合排序分布不均匀的数据。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值