基数排序(Radix Sort)

动图演示地址(​​https://www.cs.usfca.edu/~galles/visualization/RadixSort.html​​​)

Java排序算法:基数排序_i++

代码结构

Java排序算法:基数排序_i++_02

Java排序算法:基数排序_i++_03

Java排序算法:基数排序_代码结构_04

Java排序算法:基数排序_git_05


package suanfa.paixu;

public class RadixSort implements Sort {

public static void main(String[] args) {
Test.test(new RadixSort());
}

public int maxbits(int[] arr) {
int max = Integer.MIN_VALUE;
for (int i = 0; i < arr.length; i++) {
max = Math.max(max, arr[i]);
}
int num = 0;
while (max > 9) {
num++;
max /= 10;
}
return num;
}

public void radixSort(int[] arr, int l, int r, int digit) {
final int radix = 10;
int[] help = new int[r - l + 1];
for (int d = 0; d <= digit; d++) {
int[] count = new int[radix];
for (int i = l; i <= r; i++) {
count[getDigit(arr[i], d)]++;
}
for (int i = 1; i < radix; i++) {
count[i] = count[i] + count[i - 1];
}
for (int i = r; i >= l; i--) {
help[--count[getDigit(arr[i], d)]] = arr[i];
}
for (int i = l, j = 0; l <= r && j < help.length; i++, j++) {
arr[i] = help[j];
}
}
}

public int getDigit(int x, int d) {
return (x / (int) Math.pow(10, d)) % 10;
}

public void sort(int[] arr) {
if (arr == null || arr.length < 2) {
return;
}
// 对负数进行正数化处理,但是有溢出的风险
int min = positive(arr);
radixSort(arr, 0, arr.length - 1, maxbits(arr));
// 还原
revert(arr, min);
}

private int positive(int[] arr) {
int min = 0;
for (int i = 0; i < arr.length; i++) {
min = Math.min(min, arr[i]);
}

if (min != 0) {
for (int i = 0; i < arr.length; i++) {
arr[i] -= min;
}
}
return min;
}

private void revert(int[] arr, int min) {
if (min != 0) {
for (int i = 0; i < arr.length; i++) {
arr[i] += min;
}
}
}
}