根据桶子法思想自己写的,目前运行正常,有没有不足还不知道
package com.www.demo06;
public class BasicData {
public static void main(String[] args) {
// int[] arr = new int[]{53,542,3,63,14,214,154,748,616,589};
int[] arr = new int[]{3,542,63,53};
sort(arr);
}
public static void sort(int[] arr){
//数据个数
int num = arr.length;
//查出这些数据最大数的位数
int max = 0;//代表最大值
for (int i = 0;i < num;i++){
if (arr[i] > max){
max = arr[i];
}
}
int units = (max + "").length();//位数
//桶子法
int[][] arr1 = new int[10][num];//十个桶
//操作桶里的数字:数组数据按照权重从低到高顺序放入桶中(放-取-放-取)
for(int k = 0; k < units;k++){//取得每一位数的方法:除以该位权重之后取模10(从低到高)
//放
for (int i = 0;i < num;i++){//对每一个数据进行处理,i代表每一位数据位置
// int temp = arr[i] / (10^k) % 10;//取出数组中数据,得到权重对应数字----试了一下,java中^作用和减法一样
int temp = arr[i] / (int)Math.pow(10, k) % 10;
for(int j = 0;j <num;j++){
if (arr1[temp][j] == 0){
arr1[temp][j] = arr[i];//按照个位数与数组下标对应的方式放置到桶里,j代表每个桶中的各个位置
break;
}
}
}
//取----按照个位数从小到大取出:先取一维再,同一维里的二维
int point = 0;//一维数组下标
for(int i = 0;i < 10;i++){//每个桶
for (int j = 0; j < num; j++) {//桶里的数据
if (arr1[i][j] != 0) {
arr[point] = arr1[i][j];//只要值不为0,那一定放数据了,不用担心point超,本来桶里放的就是arr中的数据
arr1[i][j] = 0;
point++;
}else{
break;
}
}
if (point == num){
break;
}
}
}
//将排序好的数字打印出来
for (int i = 0;i < num;i++){
System.out.println(arr[i]);
}
}
}
时间复杂度:k/2*num^2(k代表位数)?
参考网上资料,对代码做了一些修改,增加一个辅助数组,用来指示每个桶中的数据个数,放数据时,不用依次判断了
package com.www.demo06;
public class BasicData1 {
public static void main(String[] args) {
int[] arr = new int[10];
for (int i = 0; i < 10;i++){
arr[i] = (int)(Math.random()*1000);
}
show(arr);
sort(arr);
show(arr);
}
public static void show(int[] arr){
for (int i = 0;i < arr.length;i++){
System.out.println(arr[i]);
}
}
public static void sort(int[] arr){
int num = arr.length;//数据个数
//查出这些数据最大数的位数:便于取出每一位数据
int max = 0;
for (int i = 0;i < num;i++){
if (arr[i] > max){
max = arr[i];
}
}//最大值,时间复杂度(num)
int units = (max + "").length();//位数
int power = (int)Math.pow(10,units);
//桶子法
int[][] arr1 = new int[10][num];//十个桶
int[] arr2 = new int[10];//辅助数组:记录每个桶中有多少数据
//操作桶里的数字:数组数据按照权重从低到高顺序放入桶中(放-取-放-取)
for(int k = 1; k < power;){//取得每一位数的方法:除以该位权重之后取模10(从低到高)
//放
for (int i = 0;i < num;i++){
int temp = arr[i] / k % 10;//每个数据对应temp桶
arr1[temp][arr2[temp]] = arr[i];
arr2[temp]++;//对于temp标号的桶,每放入一个数据,下标就向后移一位
}//时间复杂度:num
//取
int point = 0;//一维数组下标
for(int i = 0;i < 10;i++){//每个桶
for (int j = 0; j < arr2[i]; j++) {//桶里的数据
arr[point] = arr1[i][j];
point++;
}
arr2[i] = 0;
}//时间复杂度:num + 10
k *= 10;
}//units(2*num+10)
}
}
看了一下别人的时间复杂度,好像比我的少
网上看了一个别人写的,桶没有设立二维数组,而是有多少数据,建立多大的一维数组
辅助数组**a[i]的值减去a[i-1]**的值表示位数为i的数据的个数
而a[i]-1的值就对应了放位数值i的桶的最大下标
这是个大致思路,具体实现这里就不放了