Java桶排序之基數(shù)排序詳解
基數(shù)排序也是桶排序的一種,也是跟樣本數(shù)據(jù)強(qiáng)相關(guān)的,且基數(shù)排序要求樣本數(shù)據(jù)是非負(fù)的十進(jìn)制數(shù),如果有小數(shù)或者負(fù)數(shù),那么代碼將要大量重寫!這就是不基于比較的排序的弊端。一般來說,我們認(rèn)為基數(shù)排序時間復(fù)雜度為O(N)。但事實上,如果數(shù)據(jù)量很大很大,它的時間復(fù)雜度是O(N*log10(Max))(
底數(shù)是10)。
基數(shù)排序算法流程不是很難,但是以下代碼實現(xiàn)方式比較騷,所以先放上一張截圖,方便查看。
我們知道基數(shù)排序的實現(xiàn)流程是需要準(zhǔn)備10個隊列的,但是經(jīng)典的實現(xiàn)流程卻是利用了一個count數(shù)組來模擬了出隊列的操作,所以節(jié)省了空間。
package com.harrison.class05; import java.util.Arrays; // 基數(shù)排序也是桶排序的一種,也是跟樣本數(shù)據(jù)強(qiáng)相關(guān)的 // 且基數(shù)排序要求樣本數(shù)據(jù)是非負(fù)的十進(jìn)制數(shù) // 如果有小數(shù)或者負(fù)數(shù),那么代碼將要大量重寫! // 這就是不基于比較的排序的弊端 // 一般來說,我們認(rèn)為基數(shù)排序時間復(fù)雜度為O(N) // 但事實上,如果數(shù)據(jù)量很大很大,它的時間復(fù)雜度是O(N*log10(Max))(底數(shù)是10) public class Code03_RadixSort { public static void radixSort(int[] arr) { if (arr == null || arr.length < 2) { return; } radixSort(arr, 0, arr.length - 1, maxBits(arr)); } // 求出數(shù)組中最大值的位數(shù) // 比如數(shù)組中最大值是100 那么返回3 public static int maxBits(int[] arr) { int max = Integer.MIN_VALUE; for (int i = 0; i < arr.length; i++) { max = Math.max(max, arr[i]); } int res = 0; while (max != 0) { res++; max /= 10; } return res; } // 此方法配合截圖理解!?。? public static void radixSort(int[] arr, int L, int R, int digit) { final int radix = 10; int i = 0, j = 0; // 原數(shù)組有多少個數(shù),準(zhǔn)備多少個空間 int[] help = new int[R - L + 1]; for (int d = 1; d <= digit; d++) { int[] count = new int[radix]; for (i = L; i <= R; i++) { j = getDigits(arr[i], d); count[j]++; } for (i = 1; i < radix; i++) { count[i] = count[i] + count[i - 1]; } for (i = R; i >= L; i--) { j = getDigits(arr[i], d); help[count[j] - 1] = arr[i]; count[j]--; } for (i = 0, j = 0; i <= R; i++, j++) { arr[i] = help[i]; } } } public static int getDigits(int x, int d) { return ((x / (int) (Math.pow(10, d - 1)))) % 10; } public static void comparator(int[] arr) { Arrays.sort(arr); } public static int[] generateRandomArray(int maxSize, int maxValue) { int[] arr = new int[(int) ((maxSize + 1) * Math.random())]; for (int i = 0; i < arr.length; i++) { arr[i] = (int) ((maxValue + 1) * Math.random()); } return arr; } public static int[] copyArray(int[] arr) { if (arr == null) { return null; } int[] res = new int[arr.length]; for (int i = 0; i < arr.length; i++) { res[i] = arr[i]; } return res; } public static boolean isEqual(int[] arr1, int[] arr2) { if ((arr1 == null && arr2 != null) || (arr1 != null && arr2 == null)) { return false; } if (arr1 == null && arr2 == null) { return true; } if (arr1.length != arr2.length) { return false; } for (int i = 0; i < arr1.length; i++) { if (arr1[i] != arr2[i]) { return false; } } return true; } public static void printArray(int[] arr) { if (arr == null) { return; } for (int i = 0; i < arr.length; i++) { System.out.print(arr[i] + " "); } System.out.println(); } public static void main(String[] args) { int testTime = 500000; int maxSize = 100; int maxValue = 100000; boolean succeed = true; for (int i = 0; i < testTime; i++) { int[] arr1 = generateRandomArray(maxSize, maxValue); int[] arr2 = copyArray(arr1); radixSort(arr1); comparator(arr2); if (!isEqual(arr1, arr2)) { succeed = false; printArray(arr1); printArray(arr2); break; } } System.out.println(succeed ? "Nice!" : "Fucking fucked!"); int[] arr = generateRandomArray(maxSize, maxValue); printArray(arr); radixSort(arr); printArray(arr); } }
總結(jié)
本篇文章就到這里了,希望能夠給你帶來幫助,也希望您能夠多多關(guān)注腳本之家的更多內(nèi)容!
相關(guān)文章
Mybatis查找返回Map,List集合類型的數(shù)據(jù)方式
這篇文章主要介紹了Mybatis查找返回Map,List集合類型的數(shù)據(jù)方式,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教2021-07-07Java實戰(zhàn)角色權(quán)限后臺腳手架系統(tǒng)的實現(xiàn)流程
只學(xué)書上的理論是遠(yuǎn)遠(yuǎn)不夠的,只有在實戰(zhàn)中才能獲得能力的提升,本篇文章手把手帶你用java+Springboot+Maven+myBaits-Plus+Vue+Element-UI+Mysql實現(xiàn)一個角色權(quán)限后臺腳手架系統(tǒng),大家可以在過程中查缺補(bǔ)漏,提升水平2022-01-01