First, have a look at this code:
Dictionary<int,int> dict = Dictionary<int,int>();
dict[3] = 1;
dict[2] = 2;
dict[1] = 3;
foreach(KeyValuePair<int,int> item in dict.OrderByDescending(p => p.Value))
{
print(item.Value);
break;
}
This code, basically prints the value of the entry in the dictionary with the highest value. I'd like to accomplish this without using a "broken" foreach
loop. How might I do that?
Well, you could do:
if(dict.Any())
print(dict.Values.Max());
This is not only more concise, but also doesn't require sorting the dictionary out-of-place first (which is what starting an enumeration onOrderByDescending
does), so is more efficient in both time and space.
If you need the key as well, you can use a MaxBy
operator (such as from moreLinq) as follows:
if(dict.Any())
{
var bestKvp = dict.MaxBy(kvp => kvp.Value);
Console.WriteLine("Key = {0}, Value = {1}", bestKvp.Key, bestKvp.Value);
}
It is possible to accomplish this with standard LINQ to Objects in O(n)
time and O(1)
space with the Aggregate
operator, but it's quite ugly:
if(dict.Any())
{
var bestKvp = dict.Aggregate((bestSoFar, next) => bestSoFar.Value > next.Value ? bestSoFar : next );
Console.WriteLine("Key = {0}, Value = {1}", bestKvp.Key, bestKvp.Value);
}
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