1 <?php 2 #基数排序,此处仅对正整数进行排序,至于负数和浮点数,需要用到补码,各位有兴趣自行研究 3 4 #计数排序 5 #@param $arr 待排序数组 6 #@param $digit_num 根据第几位数进行排序 7 function counting_sort(&$arr, $digit_num = false) { 8 if ($digit_num !== false) { #如果参数$digit_num不为空,则根据元素的第$digit_num位数进行排序 9 for ($i = 0; $i < count($arr); $i++) { 10 $arr_temp[$i] = get_specific_digit($arr[$i], $digit_num); 11 } 12 } else { 13 $arr_temp = $arr; 14 } 15 16 $max = max($arr); 17 $time_arr = array(); #储存元素出现次数的数组 18 19 #初始化出现次数数组 20 for ($i = 0; $i <= $max; $i++) { 21 $time_arr[$i] = 0; 22 } 23 24 #统计每个元素出现次数 25 for ($i = 0; $i < count($arr_temp); $i++) { 26 $time_arr[$arr_temp[$i]]++; 27 } 28 29 #统计每个元素比其小或相等的元素出现次数 30 for ($i = 0; $i < count($time_arr) - 1; $i++) { 31 $time_arr[$i + 1] += $time_arr[$i]; 32 } 33 34 #利用出现次数对数组进行排序 35 for($i = count($arr) - 1; $i >= 0; $i--) { 36 $sorted_arr[$time_arr[$arr_temp[$i]] - 1] = $arr[$i]; 37 $time_arr[$arr_temp[$i]]--; 38 } 39 40 $arr = $sorted_arr; 41 ksort($arr); #忽略这次对key排序的效率损耗 42 } 43 44 #计算某个数的位数 45 function get_digit($number) { 46 $i = 1; 47 while ($number >= pow(10, $i)) { 48 $i++; 49 } 50 51 return $i; 52 } 53 54 #获取某个数字的从个位算起的第i位数 55 function get_specific_digit($num, $i) { 56 if ($num < pow(10, $i - 1)) { 57 return 0; 58 } 59 return floor($num % pow(10, $i) / pow(10, $i - 1)); 60 } 61 62 #基数排序,以计数排序作为子排序过程 63 function radix_sort(&$arr) { 64 #先求出数组中最大的位数 65 $max = max($arr); 66 $max_digit = get_digit($max); 67 68 for ($i = 1; $i <= $max_digit; $i++) { 69 counting_sort($arr, $i); 70 } 71 } 72 73 74 $arr = array(1, 33, 44, 33, 33, 21, 521, 5, 4444, 91, 700, 8, 0); 75 radix_sort($arr); 76 77 print_r($arr); 78 ?>
Array ( [0] => 0 [1] => 1 [2] => 5 [3] => 8 [4] => 21 [5] => 33 [6] => 33 [7] => 33 [8] => 44 [9] => 91 [10] => 521 [11] => 700 [12] => 4444 )