久久精品人人爽,华人av在线,亚洲性视频网站,欧美专区一二三

C#程序中怎么使用泛型集合代替非泛型集合

154次閱讀
沒有評論

共計 3287 個字符,預計需要花費 9 分鐘才能閱讀完成。

C# 程序中怎么使用泛型集合代替非泛型集合,相信很多沒有經驗的人對此束手無策,為此本文總結了問題出現的原因和解決方法,通過這篇文章希望你能解決這個問題。

軟件開發過程中,不可避免會用到集合,C# 中的集合表現為數組和若干集合類。不管是數組還是集合類,它們都有各自的優缺點。如何使用好集合是我們在開發過程中必須掌握的技巧。不要小看這些技巧,一旦在開發中使用了錯誤的集合或針對集合的方法,應用程序將會背離你的預想而運行。

使用泛型集合代替非泛型集合

如果要讓代碼高效運行,應該盡量避免裝箱和拆箱,以及盡量減少轉型。很遺憾,在微軟提供給我們的第一代集合類型中沒有做到這一點,下面我們看 ArrayList 這個類的使用情況:

 ArrayList al=new ArrayList(); al.Add(0); al.Add(1); al.Add(mike  foreach (var item in al) { Console.WriteLine(item); }

上面這段代碼充分演示了我們可以將程序寫得多么糟糕。

首先,ArrayList 的 Add 方法接受一個 object 參數,所以 al.Add(1) 首先會完成一次裝箱;其次,在 foreach 循環中,待遍歷到它時,又將完成一次拆箱。

在這段代碼中,整形和字符串作為值類型和引用類型,都會先被隱式地強制轉型為 object,然后在 foreach 循環中又被轉型回來。

同時,這段代碼也是非類型安全的:我們然 ArrayList 同時存儲了整型和字符串,但是缺少編譯時的類型檢查。雖然有時候需要有意這樣去實現,但是更多的時候,應該盡量避免。缺少類型檢查,在運行時會帶來隱含的 Bug。集合類 ArrayList 如果進行如下所示的運算,就會拋出一個 IvalidCastException:

 ArrayList al=new ArrayList(); al.Add(0); al.Add(1); al.Add(mike  int t = 0; foreach (int item in al) { t += item; }

ArrayList 同時還提供了一個帶 ICollection 參數的構造方法,可以直接接收數組,如下所示:

var intArr = new int[] {0, 1, 2, 3};ArrayList al=new ArrayList(intArr);

該方法內部實現一樣糟糕,如下所示(構造方法內部最終調用了下面的 InsertRange 方法):

public virtual void InsertRange(int index, ICollection c){ if (c == null) { throw new ArgumentNullException( c , Environment.GetResourceString( ArgumentNull_Collection)); } if ((index   0) || (index   this._size)) { throw new ArgumentOutOfRangeException( index , Environment.GetResourceString( ArgumentOutOfRange_Index)); } int count = c.Count; if (count   0) { this.EnsureCapacity(this._size + count); if (index   this._size) { Array.Copy(this._items, index, this._items, index + count, this._size - index); } object[] array = new object[count]; c.CopyTo(array, 0); array.CopyTo(this._items, index); this._size += count; this._version++; }}

概括來講,如果對大型集合進行循環訪問、轉型或裝箱和拆箱操作,使用 ArrayList 這樣的傳統集合對效率影響會非常大。鑒于此,微軟提供了對泛型的支持。泛型使用一對 括號將實際類型括起來,然后編譯器和運行時會完成剩余的工作。微軟也不建議大家使用 ArrayList 這樣的類型了,轉而建議使用它們的泛型實現,如 List T。

注意,非泛型集合在 System.Collections 命名空間下,對應的泛型集合則在 System.Collections.Generic 命名空間下。

建議一開始的那段代碼的泛型實現為:

List int  intList = new List int  intList.Add(1); intList.Add(2); //intList.Add(mike  foreach (var item in intList) { Console.WriteLine(item); }

代碼中被注釋的那一行不會被編譯通過,因為“mike 不是整型,這里就體現了類型安全的特點。

下面比較了非泛型集合和泛型集合在運行中的效率:

 static void Main(string[] args) { Console.WriteLine( 開始測試 ArrayList:  TestBegin(); TestArrayList(); TestEnd(); Console.WriteLine(開始測試 List T :  TestBegin(); TestGenericList(); TestEnd(); } static int collectionCount = 0; static Stopwatch watch = null; static int testCount = 10000000; static void TestBegin() { GC.Collect(); // 強制對所有代碼進行即時垃圾回收  GC.WaitForPendingFinalizers(); // 掛起線程,執行終結器隊列中的終結器(即析構方法) GC.Collect(); // 再次對所有代碼進行垃圾回收,主要包括從終結器隊列中出來的對象  collectionCount = GC.CollectionCount(0); // 返回在 0 代碼中執行的垃圾回收次數  watch = new Stopwatch(); watch.Start(); } static void TestEnd() { watch.Stop(); Console.WriteLine(耗時: + watch.ElapsedMilliseconds.ToString()); Console.WriteLine(垃圾回收次數: + (GC.CollectionCount(0) - collectionCount)); } static void TestArrayList() { ArrayList al = new ArrayList(); int temp = 0; for (int i = 0; i   testCount; i++) { al.Add(i); temp = (int)al[i]; } al = null; } static void TestGenericList() { List int  listT = new List int  int temp = 0; for (int i = 0; i   testCount; i++) { listT.Add(i); temp = listT[i]; } listT = null; }

輸出為:

開始測試 ArrayList:

耗時:2375

垃圾回收次數:26

開始測試 List T :

耗時:220

垃圾回收次數:5

看完上述內容,你們掌握 C# 程序中怎么使用泛型集合代替非泛型集合的方法了嗎?如果還想學到更多技能或想了解更多相關內容,歡迎關注丸趣 TV 行業資訊頻道,感謝各位的閱讀!

正文完
 
丸趣
版權聲明:本站原創文章,由 丸趣 2023-07-28發表,共計3287字。
轉載說明:除特殊說明外本站除技術相關以外文章皆由網絡搜集發布,轉載請注明出處。
評論(沒有評論)
主站蜘蛛池模板: 南漳县| 黄龙县| 宣武区| 万山特区| 黎川县| 富蕴县| 厦门市| 全南县| 虎林市| 隆尧县| 安达市| 岚皋县| 慈利县| 莱阳市| 同江市| 黎平县| 婺源县| 子洲县| 大宁县| 南安市| 托里县| 威海市| 名山县| 龙井市| 平遥县| 兴隆县| 正宁县| 霸州市| 普宁市| 宁南县| 余庆县| 南召县| 元谋县| 盐城市| 阿拉善右旗| 山东省| 浦县| 正宁县| 雅安市| 梅州市| 全州县|