Using Lookup For Duplicate Key Value Pairs Dictionary

Have you ever had a requirement for duplicate key and value pairs in a dictionary? Sounds crazy!!! But yes, a few days ago I needed a map/dictionary with multiple entries of the same key but different values and then perform some operation like groupby and get the count blah.. blah...

So I couldn't use the Dictionary object to fulfill my requirement. The following shows what you'll get if you try to insert multiple keys inside a normal Dictionary object:

LookUp1.jpg

So I Googled around and finally endup reading a post by Jon Skeet explaining how to use LookUp for this problem. Well I was enlightened by the awesome post and decided to explore the Lookup class and its usage.

Well in the screenshot you can see that you cannot insert duplicate entries in a Dictionary class so you do need a custom list to store those values. Here's the sample code where I've created a simple data class that is holding my key and value pairs; it is:

public class Data
{
    public string Key { get; set; }
    public int Value { get; set; }
}

Now you can use a List<Data> to store those items in this:

List<Data> keyValuePairs = new List<Data>();
keyValuePairs.Add(new Data { Key = "key1", Value = 1 });
keyValuePairs.Add(new Data { Key = "key1", Value = 1 });
keyValuePairs.Add(new Data { Key = "key2", Value = 3 });
keyValuePairs.Add(new Data { Key = "key3", Value = 4 });
keyValuePairs.Add(new Data { Key = "key3", Value = 5 });
keyValuePairs.Add(new Data { Key = "key4", Value = 6 });

But this is not the actual key value pair collection we need. So, you are all familiar with LINQ and its Extension methods on any IEnumerable. Just checkout the ToLookup function, this is what we'll use to convert this list to an key value pair collection.

var groupedData = keyValuePairs.ToLookup(x => x.Key, x => x.Value);

Now we have this groupedData collection that is of type IGroupInfo<string, int> in our case. We can use that to apply the grouping operations and find the multiple values related to a Key, as in:

foreach (IGrouping<string, int> item in groupedData)
{
    Console.Write(item.Key);
    Console.Write(": ");
    foreach (var value in item)
    {
        Console.Write(value + " ");
    }
    Console.WriteLine();
}

When you run this program you'll get the output:

LookUp2.jpg

Beautiful !! isn't it? We got all the keys and corresponding values in place.

You can ask, if it's a dictionary then would I be able to get the values corresponding to a key using indexer? The answer is: yes.

Go ahead and use the indexer of keys and get all the values as IEnumerable. Check this out:

Console.Write("Key3: ");
foreach (var value in groupedData["key3"])
{
    Console.Write(value + " ");
}

Output

LookUp3.jpg

This was my first encounter with Lookup and I liked it. Hope you feel the same.


Similar Articles