基於桶的排序之計數排序

基於桶的排序之計數排序

作者:Grey

原文地址:

博客園:基於桶的排序之計數排序

CSDN:基於桶的排序之計數排序

說明

基於桶的排序有兩種,分別是計數排序基數排序

但是這兩種排序應用範圍有限,需要樣本的數據狀況滿足桶的劃分

計數排序

這個排序適用於非負數數組,如果包含負數,需要先將負數轉換成正數,處理邏輯如下

如果數組最小值是負數,假設最小值爲 min,則把數組中所有的數加上(-min),就轉換成了非負數組,最後排序結束後,再統一減去(-min)即可。

整個排序流程如下,首先獲取到整個數組的最大值,假設是 max,則可以確定,數組中的所有數都不超過 max,所以,只需要開闢一個長度爲 max + 1 的數組,假設爲 helper,然後遍歷原始數組 arr, 將

helper[arr[i]]++

helper[i] 表示原始數組中 i 這個值出現的的次數

最後從 0 到 max 依次取出 helper 數組中的非 0 值,就是排序後的結果。

例如: arr 數組是如下數據

int[] arr = {1,4,3,3,6,4,5}

arr 中的最大值是 6,得到的 helper 數組長度是 7,每個數出現的次數記錄在 helper 中以後,helper 數組如下:

int[] helper = {0,1,0,2,2,1,1}

然後找 helper 中不等於 0 的值,

helper[1] = 1; // 1 這個值出現了1次
helper[3] = 2; // 3 這個值出現了2次
helper[4] = 2; // 4 這個值出現了2次
helper[5] = 1; // 5 這個值出現了1次
helper[6] = 1; // 6 這個值出現了1次

然後按順序依次寫回 arr 中去

int[] arr = {1, 3, 3, 4, 4, 5, 6}

完整代碼如下

public class Code_CountSort {
  // 非負數
  public static void countSort(int[] arr) {
    if (null == arr || arr.length <= 1) {
      return;
    }
    int max = arr[0];
    for (int i = 1; i < arr.length; i++) {
      max = Math.max(arr[i], max);
    }
    int[] help = new int[max + 1];
    for (int j : arr) {
      help[j]++;
    }
    int t = 0;
    for (int i = 0; i < help.length; i++) {
      while (help[i] != 0) {
        arr[t++] = i;
        help[i]--;
      }
    }
  }
}

時間複雜度爲O(N),額外空間複雜度爲O(M),其中 M 是數組的最大值。

更多

算法和數據結構筆記

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章