3

I have declared a dictionary like this:

Dictionary<string, KeyValuePair<string, string>> dc = new Dictionary<string, KeyValuePair<string, string>>();

now how can I loop through it? I wanted something like the following so I created that dictionary:

name1 oldValue1 newValue1

name2 oldValue2 newValue2

...

asked Oct 5, 2011 at 13:59
9
  • I would use a Tuple instead of a KeyValuePair. But that's just me. Commented Oct 5, 2011 at 14:02
  • Can you explain what this dictionary is for? It is a somewhat strange thing to do to map a key to a key-value pair. There might be a better data structure to do what you want. Are the "old" and "new" values actually keys and values? It doesn't sound like the old value is a key; it sounds like it is a value. Commented Oct 5, 2011 at 14:05
  • @EricLippert It seems like he's using KeyValuePair to store an old value of something in the key and the new value in value. Commented Oct 5, 2011 at 14:05
  • If you are using C# 4.0, you should use Tuple<string, string> instead of KeyValuePair<> (unless clearly you are recycling the KeyValuePair of another dictionary) Commented Oct 5, 2011 at 14:08
  • 4
    This seems dangerous and error prone, to put a value in a field called "Key". Structs are cheap; why don't you just make a struct Replacement<T> { public T OldValue { get; private set; } public T NewValue { get; private set; } ... and use that? I once spent several hours debugging code where some bozo had decided to store left, top, width and height of a rectangle in a struct with fields named left, top, right, bottom because he was too lazy to define a struct with the correct names. It was extremely difficult to debug because half the names were wrong. Commented Oct 5, 2011 at 15:14

2 Answers 2

6

You can loop through it like so

foreach (var pair in dc)
{
 string name = pair.Key;
 string oldValue = pair.Value.Key;
 string newValue = pair.Value.Value;
 // use the values 
}

But I have a feeling you're using the wrong tool for the job. It sounds to me like you really need to go ahead and define a proper class to hold the names and values, and then just work with a List<T> of that class.

answered Oct 5, 2011 at 14:01
Sign up to request clarification or add additional context in comments.

5 Comments

Nice! you are right also about using the class instead of a dictionary, that way my previous question: stackoverflow.com/questions/7615640/…
You can probably use the Tuple<> class, instead of creating your own (if you're lazy like me :))
@SaguiItay: yes Tuple was a better choice but it is only on .NET 4.0 and other team members still have VS2008 installed.
@Saguiltay, the problem with Tuple<> is similar to the problem with the Dictionary approach. If you're using it inside a method as an implementation detail and nobody ever has to see it, maybe you go ahead and use it. If you start passing it around for use by other methods, it's definitely time to give it the class treatment, so that it can self-document what it contains. tuple.Item1 and tuple.Item2 tells me nothing. theClass.Name and theClass.SomeValue tells me quite a lot.
Even if not passing it around, a class is often justified, as it provides documentation for the poor maintenance programmer that comes back to the code 6 months later and has no idea what the author intended with the .Item1 and .Item2 or the .Key, .Value.Key, .Value.Value. Don't be hesitant to use classes, even for the "trivial" things.
5
foreach( KeyValuePair<string, string> kvp in dc )
{
 Console.WriteLine("Key = {0}, Value = {1}", kvp.Key, kvp.Value);
}

When you loop a dictionary you use KeyValuePair that is generic. Since your dictionary contain the key as string and the value as string, this one will take also a string for both.

You can access the key with kvp.Key and the value with kvp.Value.

For your example, you are using a Dictionary of string that contain a value of KeyValuePair. So, you can have the exact print you want with :

foreach( KeyValuePair<string, KeyValuePair<string,string>> kvp in dc )
{
 Console.WriteLine(kvp.Key + " " + kvp.Value.Key + " "+ kvp.Value.Value);
}
answered Oct 5, 2011 at 14:00

3 Comments

Good only if you put dc.Values
His dictionary's value is not a string it's a KeyValuePair<string, string>.
You know, it's still wrong. The second part should be KeyValuePair<string, KeyValuePair<string, string>>

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.