標籤:轉換 ons 結束 color white c# 為我 序列 return
迭代器
迭代器模式是和為模式的一種範例,我們訪問資料序列中所有的元素,不用關心序列是什麼類型。從資料管道中資料經過一系列不同的轉換或過濾後從管道的另一端出來。
像數組、集合等已經內建了迭代器,我們可以直接進行foreach,而我們自訂的類型,自然是無法進行這個操作的,對於自訂的類型實現迭代器模式通過IEnumerable和IEnumerator介面(或泛型介面)進行實現。在C#1.0中我們自訂類型實現迭代器是非常繁瑣的
自訂迭代器
想要對IterationSample進行foreach,首先繼承IEnumerable介面,會有一個GetEnumerator的方法需要去實現,這時建立另一個類實現IEnumerator介面,實現MoveNext方法與Current屬性,我們需要進行位置的處理
這時就可以使用foreach這個"文法糖"進行遍曆了,為什麼說是文法糖呢, 因為這隻是微軟進行的一個封裝處理,編譯成IL過後還是會看到調用了GetEnumerator、MoveNext以及Current
這裡在C#2.0中變的簡單了,這時使用yield return就可以代替整個IterationSampleIterator這個類。
Yield return會告訴編譯器這不是一個普通方法,而是實現迭代器塊的方法。
這時可能會有疑問,都yield return了是不是代表方法結束了,並不是這樣的,yield return 不代表方法執行結束 ,而是會在這裡暫時退出。Yield return內部會為我們產生一個狀態機器,去維護MoveNext方法與Current屬性
這時也許想要看看IL會產生什麼樣的代碼呢,
可以看到有state(狀態)current(當前屬性)index(索引),用來記錄塊中位置以及局部變數的值 ,其實看起來和IterationSampleIterator類似,只不過幫我們去做了這個事
可能會對暫時退出產生疑問
下面寫一個這樣的例子協助理解,在yield return前與後都有相應的輸入,for迴圈三次,在方法最後列印方法結束
下面進行調用
可以看到以下輸入,可以看到第一次執行MoveNext方法才會運行CreateEnumerable方法,也就是foreach是懶惰的,可以看到yield return方法就暫時退出了,只輸出了yield return 前,下一次movenext會從上次的位置繼續執行輸出yield return後,迴圈結束後才會輸出方法結束
除了yield return,還有yield break,這才是真正的直接退出相當與普通方法的return
使用自訂迭代器,可以簡化對類型的遍曆,有時我們需要讀取檔案中的第每一行,這樣的代碼經常會用到 。實現迭代器模型可以更加簡化代碼。
C#2.0 迭代器