基数排序(英语:Radix sort)是一种非比较型整数排序算法,其原理是将整数按位数切割成不同的数字,然后按每个位数分别比较。由于整数也可以表达字符串(比如名字或日期)和特定格式的浮点数,所以基数排序也不是只能使用于整数。基数排序的发明可以追溯到1887年赫尔曼·何乐礼打孔卡片制表机(Tabulation Machine)上的贡献[1]

它是这样实现的:将所有待比较数值(正整数)统一为同样的数字长度,数字较短的数前面补零。然后,从最低位开始,依次进行一次排序。这样从最低位排序一直到最高位排序完成以后,数列就变成一个有序序列。

import java.util.Arrays;

public class RadixSort {

    public int[] sort(int[] sourceArray) throws Exception {
// 对 arr 进行拷贝,不改变参数内容
int[] arr = Arrays.copyOf(sourceArray, sourceArray.length); int maxDigit = getMaxDigit(arr);
return radixSort(arr, maxDigit);
} /**
* 获取最高位数
*/
private int getMaxDigit(int[] arr) {
int maxValue = getMaxValue(arr);
return getNumLenght(maxValue);
} private int getMaxValue(int[] arr) {
int maxValue = arr[0];
for (int value : arr) {
if (maxValue < value) {
maxValue = value;
}
}
return maxValue;
} protected int getNumLenght(long num) {
if (num == 0) {
return 1;
}
int lenght = 0;
for (long temp = num; temp != 0; temp /= 10) {
lenght++;
}
return lenght;
} private int[] radixSort(int[] arr, int maxDigit) {
int mod = 10;
int dev = 1; for (int i = 0; i < maxDigit; i++, dev *= 10, mod *= 10) {
// 考虑负数的情况,这里扩展一倍队列数,其中 [0-9]对应负数,[10-19]对应正数 (bucket + 10)
int[][] counter = new int[mod * 2][0]; for (int j = 0; j < arr.length; j++) {
int bucket = ((arr[j] % mod) / dev) + mod;
counter[bucket] = arrayAppend(counter[bucket], arr[j]);
} int pos = 0;
for (int[] bucket : counter) {
for (int value : bucket) {
arr[pos++] = value;
}
}
} return arr;
} /**
* 自动扩容,并保存数据
*
* @param arr
* @param value
*/
private int[] arrayAppend(int[] arr, int value) {
arr = Arrays.copyOf(arr, arr.length + 1);
arr[arr.length - 1] = value;
return arr;
} public static void main(String[] args) {
int[] array = {5, 7, 17, 3, 5, 22, 4, 15, 8, 6, 4, 1, 2};
RadixSort radixSort = new RadixSort();
try {
int[] sortedArray = radixSort.sort(array);
for (int i = 0; i < sortedArray.length; i++) {
System.out.print(sortedArray[i] + " ");
}
} catch (Exception e) {
e.printStackTrace();
}
}
}

运行结果:

1 2 3 4 4 5 5 6 7 8 15 17 22

java算法 -- 基数排序的更多相关文章

  1. JAVA算法系列 冒泡排序

    java算法系列之排序 手写冒泡 冒泡算是最基础的一个排序算法,简单的可以理解为,每一趟都拿i与i+1进行比较,两个for循环,时间复杂度为 O(n^2),同时本例与选择排序进行了比较,选择排序又叫直 ...

  2. JAVA算法系列 快速排序

    java算法系列之排序 手写快排 首先说一下什么是快排,比冒泡效率要高,快排的基本思路是首先找到一个基准元素,比如数组中最左边的那个位置,作为基准元素key,之后在最左边和最右边设立两个哨兵,i 和 ...

  3. 经典排序算法 - 基数排序Radix sort

    经典排序算法 - 基数排序Radix sort 原理类似桶排序,这里总是须要10个桶,多次使用 首先以个位数的值进行装桶,即个位数为1则放入1号桶,为9则放入9号桶,临时忽视十位数 比如 待排序数组[ ...

  4. java算法 蓝桥杯 乘法运算

    问题描述 编制一个乘法运算的程序. 从键盘读入2个100以内的正整数,进行乘法运算并以竖式输出. 输入格式 输入只有一行,是两个用空格隔开的数字,均在1~99之间(含1和99). 输出格式 输出为4行 ...

  5. java算法 蓝桥杯 扶老奶奶街

    一共有5个红领巾,编号分别为A.B.C.D.E,老奶奶被他们其中一个扶过了马路. 五个红领巾各自说话: A :我和E都没有扶老奶奶 B :老奶奶是被C和E其中一个扶过大街的 C :老奶奶是被我和D其中 ...

  6. java算法 蓝桥杯 高精度加法

    问题描述 在C/C++语言中,整型所能表示的范围一般为-231到231(大约21亿),即使long long型,一般也只能表示到-263到263.要想计算更加规模的数,就要用软件来扩展了,比如用数组或 ...

  7. java算法 蓝桥杯 格子位置

    问题描述 输入三个自然数N,i,j (1<=i<=N,1<=j<=N),输出在一个N*N格的棋盘中,与格子(i,j)同行.同列.同一对角线的所有格子的位置. 输入格式 输入共三 ...

  8. java算法----排序----(6)希尔排序(最小增量排序)

    package log; public class Test4 { /** * java算法---希尔排序(最小增量排序) * * @param args */ public static void ...

  9. java算法----排序----(5)归并排序

    package log; import java.util.Arrays; public class Test4 { /** * java算法---归并排序 * * @param args */ pu ...

随机推荐

  1. 注入 Istio sidecar

    注入 Istio sidecar 网格中的每个 Pod 都必须伴随一个 Istio 兼容的 Sidecar 一同运行. 下文中将会介绍两种把 Sidecar 注入到 Pod 中的方法:使用 istio ...

  2. 03-JavaScript语法介绍

    本篇主要关于原生JavaScript的介绍,其中包括其嵌入HTML页面方式,JavaScript的语法结构,以及贪吃蛇案例: 一.绪论 JavaScript是运行在浏览器端的脚步语言,JavaScri ...

  3. C++ STL hash表用法

    C++ STL unordered_map用法 在C++11中,unordered_map作为一种关联容器,替代了hash_map,unordered_map的底层实现是hash表,所以被称为无序关联 ...

  4. Python并发编程-queue

    Python并发编程-queue 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 一.Queue # !/usr/bin/env python # _*_conding:utf-8_ ...

  5. 如果在使用谷歌的gson的时候,在返回时间类型的数据的时候,

    可能会出现在long类型的时间后面多3个0 如下图所示 可以自己创建一个json序列化的类 public class Date2LongSerializer extends JsonSerialize ...

  6. Java——CaptchaUtil生成二维码乱码

    前言 这个问题就是因为Linux上没有字体,你可以有两种方法,一个在生成的时候设置字体,一个就是安装字体. 默认的字体为Courier 乱码情况 步骤 安装字体工具 yum install -y fo ...

  7. 关于git clone远程仓库账户密码错误的问题

    这两天刚使用coding和git,但是在我第一次克隆coding上的项目的时候,提示输入账户和密码,当时我不知道这个账户和密码是指的哪个,就随便输入了,然后提示错误,,,,,, 之后每次克隆的时候都提 ...

  8. git merge与git rebase区别(转载)

    这是最近看的讲的比较通俗易懂的rebase与merge的区别了 https://www.jianshu.com/p/4079284dd970

  9. Mixed Far-Field and Near-Field Source Localization Based on Subarray Cross-Cumulant

    基于子阵列互累积量(Cross-Cumulant)的远场和近场混合声源定位[1]. 文中采用Uniform linear array (ULA)阵列,将其分为两个互相重叠的子阵列,构建关于子阵列输出信 ...

  10. pkgconfig

    # tree hiredis/ hiredis/└── usr └── local ├── include │   └── hiredis │   ├── adapters │   │   ├── a ...