1. 程式人生 > >桶排序 C# 0(1)的輔助空間,o(n)的時間複雜度進行排序,資料量有上萬條。

桶排序 C# 0(1)的輔助空間,o(n)的時間複雜度進行排序,資料量有上萬條。

</pre><pre code_snippet_id="589148" snippet_file_name="blog_20150126_1_6516364" name="code" class="csharp">protected void Page_Load(object sender, EventArgs e)
    {
        int[] arr = new int[]{ 10, 5, 1, 2, 9, 8, 6, 4, 7, 3,2,2,33,4,55 };// { 11, 13, 14, 6, 4, 12, 8, 11, 12, 9, 12 };
        Print(arr);
        Response.Write("<br>");
        arr = bucketSort(arr);
        Print(arr);       
    }
 void Print(int[] a)
    {
        for (int i = 0; i < a.Length; i++)
        {
           Response.Write(a[i].ToString()+" ");
        }       
    }  

    /// <summary>
    /// 桶排序
    /// </summary>
    /// <param name="arr"> 要排序的陣列 </param>
    /// <returns> 排序後的陣列 </returns>
    private static int[] bucketSort(int[] arr)
    {
        int max = arr.Max();
        int elementsNumber = arr.Length;

        // 初始化桶
        LinkedList<int>[] bucket = new LinkedList<int>[arr.Length];
        for (int i = 0; i < elementsNumber; i++)
        {
            bucket[i] = new LinkedList<int>();
        }
        // 元素分裝各個桶中
        for (int i = 0; i < elementsNumber; i++)
        {
            int bucketIndex = arr[i] * elementsNumber / (max + 1);
            InsertIntoLinkList(bucket[bucketIndex], arr[i]);
        }
        // 從各個桶中獲取後排序插入
        int index = 0;
        for (int i = 0; i < elementsNumber; i++)
        {
            foreach (var item in bucket[i])
            {
                arr[index++] = item;
            }
        }
        return arr;
    }

    /// <summary>
    /// 按升序插入 linklist 
    /// </summary>
    /// <param name="linkedList"> 要排序的連結串列 </param>
    /// <param name="num"> 要插入排序的數字 </param>
    private static void InsertIntoLinkList(LinkedList<int> linkedList, int num)
    {
        // 連結串列為空時,插入到第一位
        if (linkedList.Count == 0)
        {
            linkedList.AddFirst(num);
            return;
        }

        else
        {
            int length = linkedList.Count;
            for (int i = 0; i < length; i++)
            {
                if (linkedList.ElementAt(i) > num)
                {
                    LinkedListNode<int> node = linkedList.Find(linkedList.ElementAt(i));
                    linkedList.AddBefore(node, num);
                    return;
                }
            }
            linkedList.AddLast(num);
        }
    }

測試通過。

桶排序 (Bucket sort)或所謂的箱排序,工作的原理是將陣列分到有限數量的桶子裡。每個桶子再個別排序(有可能再使用別的排序演算法或是以遞迴方式繼續使用桶排序進行排序)。桶排序是鴿巢排序的一種歸納結果。當要被排序的陣列內的數值是均勻分配的時候,桶排序使用線性時間(Θ(n))。但桶排序並不是 比較排序,他不受到 O(n log n) 下限的影響,速度是比較快的。

步驟:

  1. 設定一個定量的陣列當作空桶子。
  2. 尋訪序列,並且把專案一個一個放到對應的桶子去。
  3. 對每個不是空的桶子進行排序。
  4. 從不是空的桶子裡把專案再放回原來的序列中。

理解:

例如待排數字   [6 2 4 1 5 9],準備10個空桶,最大數個空桶

[6 2 4 1 5 9]           待排陣列

[0 0 0 0 0 0 0 0 0 0]   空桶

[0 1 2 3 4 5 6 7 8 9]   桶編號(實際不存在)

1. 順序從待排陣列中取出數字,首先6被取出,然後把6入6號桶,這個過程類似這樣:空桶[ 待排陣列[ 0 ] ] = 待排陣列[ 0 ]

[6 2 4 1 5 9]           待排陣列
[0 0 0 0 0 0 6 0 0 0]   空桶
[0 1 2 3 4 5 6 7 8 9]   桶編號(實際不存在)

2. 順序從待排陣列中取出下一個數字,此時2被取出,將其放入2號桶,是幾就放幾號桶

[6 2 4 1 5 9]           待排陣列
[0 0 2 0 0 0 6 0 0 0]   空桶
[0 1 2 3 4 5 6 7 8 9]   桶編號(實際不存在)

3.  剩餘元素過程一樣,全部入桶後變成下邊這樣

[6 2 4 1 5 9]           待排陣列
[0 1 2 0 4 5 6 0 0 9]   空桶
[0 1 2 3 4 5 6 7 8 9]   桶編號(實際不存在)

4. 0表示空桶,跳過,順序取出即可:1 2 4 5 6 9