問題起源於本人的一個練手的撲克牌程序:洗完牌以後要發給場上的三人。
只發給單我的的時候用 foreach 循環一下就行了,但三我的就有點麻煩了。
牌組用list
for (int i = 0; i < PreCard.Count; i++) { a.Add(PreCard[i++]); b.Add(PreCard[i++]); c.Add(PreCard[i]); }
或者這樣寫c#
int i = 0; do { a.Insert(i, PreCard[0]); b.Insert(i, PreCard[1]); c.Insert(i, PreCard[2]); PreCard.RemoveRange(0, 3); i++; } while (i < PreCard.Count);
但若是還想使用相似迭代器的方法,那麼可使用 GetEnumerator(),由於咱們知道 foreach 裏面實際上就是調用了這個方法。
因此咱們還能夠直接調用 GetEnumerator 和 MoveNext 來進行迭代:3d
IEnumerator ie = PreCard.GetEnumerator(); while(ie.MoveNext()) { a.Add(ie.Current.ToString()); ie.MoveNext(); b.Add(ie.Current.ToString()); ie.MoveNext(); c.Add(ie.Current.ToString()); }
若是是直接把上面的代碼搬過來,會發現add方法那裏會報錯,須要提供兩個參數,鍵和值。
難道必需要對獲得的 IEnumerator 再用一次 GetEnumerator?
實際上大可沒必要,由於針對這種鍵值對,咱們有一個玩意叫作 IDictionaryEnumerator。看名字就知道它就是爲此而生的。code
IDictionaryEnumerator ie = dict.GetEnumerator(); while(ie.MoveNext()) { a.Add(ie.Key.ToString(),Convert.ToInt32(ie.Value)); ie.MoveNext(); b.Add(ie.Key.ToString(),Convert.ToInt32(ie.Value)); ie.MoveNext(); c.Add(ie.Key.ToString(),Convert.ToInt32(ie.Value)); }
至此咱們經過寫手動擋的 foreach ,成功的實現了可迭代對象間的賦值。htm
在C#中 foreach 語句,可以進行比for循環語句更直接和簡單的對集合的迭代,編譯器會將 foreach 編譯來調用 GetEnumerator 和 MoveNext方法以及Current屬性。對象
實際上 foreach 語句編譯以後也會產生相似於上面所寫的代碼。實際上這幅圖能夠比較清楚的說明一切。blog
固然你也能夠看看我寫的這篇隨筆,瞭解更多細節https://www.cnblogs.com/AD-milk/p/12459944.html編譯器
其實前面的作法都是捨近求遠....
string
我一開始寫的時候,以爲那樣作還挺好的。甚至還自信滿滿的點了發送到首頁[捂臉]
而後....固然是立刻就被撤了。我固然是不服的(聲音減弱),因而就發郵件詢問。
結果固然就是被管理員教育了,其實管理員挺耐心,教會了我不少。(隔着屏幕我也不知道對面想不想順着網線打我)
若是你還想保留原來的集合的話,那麼用上面的方法是可行的,若是不想的話,那麼像下面那樣使用linq
會更好。it
下面就給你們分享更正一下我學到的知識:
var PreCard = new Queue<string>() ; PreCard.Enqueue("03a"); PreCard.Enqueue("03b"); PreCard.Enqueue("03c"); PreCard.Enqueue("03d"); PreCard.Enqueue("04a"); PreCard.Enqueue("04b"); var players = new List<List<string>> { new List<string>(), new List<string>(), new List<string>() }; while (PreCard.Count > 0) { players.ForEach(p => p.Add(PreCard.Dequeue())); } players.ForEach(p => { p.ForEach(c => Console.Write(c + " ")); Console.WriteLine(); });
對於字典,可使用KeyValuePair
:
var PreCard = new Queue<KeyValuePair<string, int>>( new Dictionary<string, int> { {"a",1 },{"b",2 },{"c",3 },{"d",4 },{"e",5 },{"f",6 } }); var players = new List<List<KeyValuePair<string, int>>> { new List<KeyValuePair<string, int>>(), new List<KeyValuePair<string, int>>(), new List<KeyValuePair<string, int>>() }; while (PreCard.Count > 0) { players.ForEach(p => p.Add(PreCard.Dequeue())); } players.ForEach(p => { p.ForEach(c => Console.Write(c + " ")); Console.WriteLine(); });
可能各位早會這樣弄了,讓各位進來實在是很差意思了。
最後說一句,linq真好用!