2013-06-11 47 views
7

我有一本字典定義爲 Dictionary<string, int> one從VAR轉換成字典<String,int>

它有一些數據,我做了以下LINQ它

var temp = one.OrderBy(r => r.Value).Select(r => r.Key).Take(5);

但現在我想將其轉換回轉化成字典

我試過用temp.ToDictionary(r => r.Key, r => r.Value);

但它告訴我:無法將lambda表達式轉換爲類型'System.Collections.Generic.IEqualityComparer',因爲它不是委託類型

如何執行此轉換?

回答

14

這是因爲你打電話給Select(r => r.Key)就丟掉了Value。如果您想將其轉換回字典,則需要將KeyValuePair保留在一起。

var temp = one.OrderBy(r => r.Value).Take(5); 

var backToDictionary = temp.ToDictionary(r => r.Key, r => r.Value); 

如果你還是希望有按鍵的IEnumerable<string>在你的問題,你可以單獨使用:

var tempKeys = temp.Select(r => r.Key); 

原因您收到一個看似無關的錯誤信息指的是IEqualityComparer是因爲編譯器試圖對您嘗試調用哪個超載做出最佳猜測。在這種情況下,它最好的猜測是認爲你試圖撥打this overload

考慮你有代碼和類型它產生:

IEnumerable<string> temp = one.OrderBy(r => r.Value).Select(r => r.Key).Take(5); 

這將產生執行IEnumerable<string>的對象。然後用你的召喚:在這種情況下

temp.ToDictionary(r => r.Key, r => r.Value); 

rstring。編譯器在這一點上嚇了一跳,因爲沒有這樣的東西,如r.Keyr.Value。它認識到有2個參數正在使用,因此有兩種可能的過載從ToDictionarythis methodthis one)中挑選。在這一點上,我不確定編譯器選擇哪一個的規則(特別是因爲它不能推斷出r.Keyr.Value的類型),但它選擇了其中的一個。 (也許它只是聲明/發現的「第一個」)或許它贊成通過lambda表達式的直接對象輸入?)無論如何,它選擇過載需要IEqualityComparer而不是Func<TSource, TElement>,並告訴你(自然地)lambda表達式是不可轉換爲IEqualityComprarer。根據我的經驗,一旦你提供了編譯器垃圾(在這種情況下爲r.Keyr.Value),重載決議就會退出窗口。 有時它可以解決問題,通常只有一個過載與數字參數匹配,或者至少沒有模糊性。但是其他時候你只能看到編譯器錯誤並修復根本問題。

+0

爲什麼錯誤提到'IEqualityComparer'?編譯器是不是應該能夠檢測到'Key'和'Value'沒有在'string'中定義? – voithos

+0

@voithos編譯器很可能試圖對你試圖調用的重載進行「最佳猜測」。我會更新我的答案。 –

+0

@voithos我已經添加了一個詳細的解釋,爲什麼這個特定的錯誤出現了。 –

相關問題