基数排序
基数排序(radix sort)又称桶排序(bucketsort),相对于常见的比较排序,基数排序是一种分配式排序,即通过将所有数字分配到应在的位置最后再覆盖到原数组完成排序的过程。我在上一篇讲到的计数排序也属于这种排序模式,上一篇结尾处提到了计数排序的稳定性,即排序前和排序后相同的数字相对位置保持不变。今天我们要说的基数排序就要利用到排序稳定性这一点。
排序过程
初始数组:[ 2, 88, 1, 8, 7, 38, 28, 72, 76, 0 ]
1.按个位排序(二维数组bucket空间没用完,就不画全了)
0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 |
---|---|---|---|---|---|---|---|---|---|
0 | 1 | 72 | 76 | 88 | |||||
8 | |||||||||
38 | |||||||||
28 |
覆盖原数组为:[ 0,1,72,76,88,8,38,28 ]
2.按百位排序(根据覆盖后的数组)
0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 |
---|---|---|---|---|---|---|---|---|---|
0 | 28 | 38 | 72 | 88 | |||||
1 | 76 | ||||||||
8 | |||||||||
再次覆盖原数组(最终顺序):[ 0,1,8,28,38,72,76,88 ]
代码如下┏ (゜ω゜)=👇
public class RadixSort{
public static void radixSort(int[] sorted,int digit){
int sortedLen = sorted.length;
//设置基数
int dig = 1;
//创建一个桶bucket
int[][] bucket = new int[sortedLen][10];
//创建每个数据个(百)位等0-9出现的记录
int[] temp = new int[10];
while(dig < digit){
以 dig 位(1 就是个位,10 就是十位,以此类推)基准,收集数据到bucket数组中
for(int num:sorted){
int d = (num / dig) % 10;
bucket[temp[d]++][d] = num;
}
int k = 0;
//根据个(百)位的顺序进行排列并覆盖原数组
for(int i = 0;i < 10;i++){
if(temp[i] != 0){
for(int j = 0;j < temp[i];j++){
sorted[k++] = bucket[j][i];
}
}
//把记录清零,防止影响下次循环
temp[i] = 0;
}
dig *= 10;
}
}
}