C# 排序技術研究與對比


一、 排序場景

  • 一維數組排序
  • 多維數組排序
  • 集合排序,例如Dictionary ,List<T>, 自定義類集合排序等
  • DataTable排序

二、 排序實現和測試

1. 一維數組排序

1.1 一維數組排序特點

    元素之間是一維線性的關系,每個元素只有一個下標,在排序場景下,每個元素的數據類型是一致的。例如:

clip_image001

1.2 C# 一維數組排序實現

A:調用Array.Sort方法實現數組排序,不限制元素數據類型,底層基於對IComparable的接口實現

clip_image003

B:使用Linq實現排序

clip_image004

1.2 測試結果對比
 

1000條數據(GUID

10000數據(GUID

100000數據(GUID

Array.Sort

2ms

35ms

420ms

Linq

4ms

74ms

738ms

可以看出, Array.Sort排序優於Linq的性能(越底層的結構,排序的性能越好)。

2. 多維數組排序

2.1 多維數組排序特點

數組可以具有多個維度,支持多行多列,各個維度的數據類型可以不同。

在此文中,交錯數組不在研究范圍內,主要研究的是不同數據類型的矩陣數組,這樣更加貼近我們在實際場景中的數據。例如:

clip_image005

2.2 C# 多維數組排序實現

Step1定義一個對象排序類ObjectComparer,實現IComparer接口,主要負責數組中某個列的排序,

如果要排序的列是int類型,進行如下比較即可:其他類推。

clip_image006

ObjectComparer類結構:

clip_image007

Step2定義維度順序整形數組:tagObjArray,實例化ObjectComparer對象,將要排序的數組作為參數傳遞給ObjectComparer的構造函數。

clip_image008

Step3調用Array.Sort方法排序,參數:維度順序整形數組:tagObjArray和ObjectComparer對象。

clip_image009

3. 集合排序

3.1.ArrayList 類

使用大小可按需動態增加的數組。

clip_image010

3.2 List 類

可通過索引訪問的對象的強類型列表。提供用於對列表進行搜索、排序和操作的方法,在決定使用 List 還是使用 ArrayList 類(兩者具有類似的功能)時, List 類在大多數情況下執行得更好並且是類型安全的。例子中的Sort其實調用的是String.Sort方法。

clip_image011

3.3 List和ArrayList性能測試對比
 

ArrayList

List

100000

498 ms

538ms

3.4 Dictionary類/SortedDictionary類

從數據結構上來說都屬於Hashtable,對關鍵字(鍵值)進行散列操作,適合鍵值對的存取,排序可以使用LINQ實現,建議使用SortedDictionary替換。

Dictionary和HashTable內部實現差不多,但前者無需裝箱拆箱操作,效率略高一點

clip_image012

clip_image013

3.5 HashTable類

Hashtable 主要用於鍵值快速查找,卻沒有提供排序的方法,所以它的排序需要借住數組或其它集合來實現。

clip_image014

HashTable中的key/value均為object類型,由包含集合元素的存儲桶組成。存儲桶是 HashTable中各元素的虛擬子組,與大多數集合中進行的搜索和檢索相比,存儲桶可令搜索和檢索更為便捷。每一存儲桶都與一個哈希代碼關聯,該哈希代碼是使用哈希函數生成的並基於該元素的鍵。HashTable的優點就在於其索引的方式,速度非常快。如果以任意類型鍵值訪問其中元素會快於其他集合,特別是當數據量特別大的時候,效率差別尤其大。

HashTable的應用場合有:對象緩存,樹遞歸算法的替代,和各種需提升效率的場合。

3.6 Stack類

Stack,棧,表示對象的簡單的后進先出非泛型集合。Push方法入棧,Pop方法出棧。

3.7 Queue類

隊列,先進先出。enqueue方法入隊列,dequeue方法出隊列。

3.8 自定義類集合

Step1:定義自定義類:Person

clip_image015

Step2:構造實體類集合:List<Person> persons

clip_image016

Step3:排序方法實現:

1、直接排序

clip_image017

2、Person實現IComparable接口,直接調用Sort方法排序

clip_image018

直接調用Sort方法排序

clip_image019

3、Linq實現排序

clip_image020

測試結果對比:

 

1.直接排序

2.實現IComparable接口

3.Linq

100000

75ms

99ms

29ms

4. DataTable排序

4.1 DataTable特點

(1)DataTable 對象是按條件區分大小寫的。(如果有兩個 DataTable對象分別為“mydatatable”和“Mydatatable”,則搜索表的字符串被認為是區分大小寫的。如果只有“mydatatable”而不存在“Mydatatable”,則該搜索表的字符串不區分大小寫)。

(2)以編程方式創建 DataTable,須先通過將 DataColumn 對象添加到 DataColumnCollection(通過 Columns 屬性訪問)中來定義其架構。

(3)向 DataTable 添加行,須使用 NewRow 方法返回新的 DataRow 對象。(DataTable 可存儲的最大行數是 16,777,216)。

(4)DataTable 也包含可用於確保數據完整性的 Constraint 對象的集合

(5)DataTable 事件(RowChanged、RowChanging、RowDeleting 和 RowDeleted)可用於確定對表進行更改的時間

4.2 DataTable排序實現

Step1: 構造DataTable

clip_image021

Step2:DataView排序

clip_image022

Step2:DataTable.Select排序

clip_image023

4.3 測試結果對比
 

1.DataView排序

2.DataTable.Select排序

100000

526 ms

368ms

對比下自定義類存儲100000條相同數據的排序結果:

測試結果對比:

 

1.直接排序

2.實現IComparable接口

3.Linq

100000

75ms

99ms

29ms

三、 排序效率總結

1、 在數組排序中,建議使用Array.Sort 方式,優於LINQ方式

2、 在自定義類排序時,推薦使用LINQ方式

3、 DataTable和自定義類存儲同類型數據時,自定義類的排序整體優於DataTable方式。

4、 DataTable排序時,推薦使用DataTable.Select排序方式。

5、 Dictionary和HashTable內部實現差不多,但Dictionary無需裝箱拆箱操作,效率略高一點。數據量較大時,建議采用HashTable。

6、 ArrayList集合的排序性能優於List集合。

7、 Stack和Queue集合用於棧和隊列操作。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM