I have a dictionary defined as
Dictionary<string, int> one
it has some data and I do the following LINQ on it
var temp = one.OrderBy(r => r.Value).Select(r => r.Key).Take(5);
But now I want to convert it back into a `Dictionary
I tried using temp.ToDictionary(r => r.Key, r => r.Value);
But it tells me: Cannot convert lambda expression to type 'System.Collections.Generic.IEqualityComparer' because it is not a delegate type
How do I do this conversion?
It's because you throw away the Value
with the call to Select(r => r.Key)
. You'll need to keep the KeyValuePair
together if you want to convert it back to a dictionary.
var temp = one.OrderBy(r => r.Value).Take(5);
var backToDictionary = temp.ToDictionary(r => r.Key, r => r.Value);
If you still want to have an IEnumerable<string>
of the keys as in your question, you can use this separately:
var tempKeys = temp.Select(r => r.Key);
The reason you're receiving a seemingly unrelated error message referring to an IEqualityComparer
is because the compiler is attempting to make a best guess as to which overload you are attempting to call. Its best guess in this case thinks you were trying to call this overload.
Consider the code you had and the type it produced:
IEnumerable<string> temp = one.OrderBy(r => r.Value).Select(r => r.Key).Take(5);
This would produce an object implementing IEnumerable<string>
. Then with your call of:
temp.ToDictionary(r => r.Key, r => r.Value);
r
in this case is string
. The compiler at this point is freaking out because there's no such thing as r.Key
nor r.Value
. It recognizes that there are 2 parameters being used, and thus has two possible overloads to pick from for ToDictionary
(this method, and this one). At this point, I'm not sure what the rules are for the compiler to choose one over the other (especially since it cannot infer the types of r.Key
or r.Value
), but it chose one of them. (perhaps it's simply the "first" one declared/found? Perhaps it favours direct object inputs over lambda expressions?) At any rate, it chooses the overload requiring an IEqualityComparer
instead of a Func<TSource, TElement>
and tells you (naturally) that a lambda expression is not convertable to IEqualityComprarer
.
In my experience, once you feed the compiler garbage (r.Key
and r.Value
in this case), overload resolution kinda goes out the window. Sometimes it works out, usually when there is only one overload that matches the number parameters, or at least no ambiguity. But other times you just gotta see past the compiler error and fix the root problem.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With