This is not a LINQ problem. Here's a generic version that will solve your problem.
static class SortedDictionaryExtensions {
public static void MergeKeys<TKey1, TKey2, TValue>(
this SortedDictionary<TKey1, SortedDictionary<TKey2, List<TValue>>> dictionary,
TKey1 intoKey,
TKey1 fromKey
) {
if (dictionary == null) {
throw new ArgumentNullException("dictionary");
}
if (intoKey == null) {
throw new ArgumentNullException("intoKey");
}
if (fromKey == null) {
throw new ArgumentNullException("fromKey");
}
SortedDictionary<TKey2, List<TValue>> to;
SortedDictionary<TKey2, List<TValue>> from;
if (!dictionary.TryGetValue(intoKey, out to)) {
throw new ArgumentOutOfRangeException("intoKey");
}
if (!dictionary.TryGetValue(fromKey, out from)) {
throw new ArgumentOutOfRangeException("fromKey");
}
foreach(TKey2 key in from.Keys) {
if (to.Keys.Contains(key)) {
to[key].AddRange(from[key]);
}
else {
to.Add(key, from[key]);
}
}
dictionary.Remove(fromKey);
}
}
Usage:
SortedDictionary<int, SortedDictionary<string, List<string>>> list =
new SortedDictionary<int, SortedDictionary<string, List<string>>>();
list.Add(2, new SortedDictionary<string, List<string>>());
list[2].Add("1000", new List<string>() { "a", "b", "c" });
list[2].Add("2000", new List<string>() { "b", "c" });
list.Add(4, new SortedDictionary<string, List<string>>());
list[4].Add("1000", new List<string>() { "z" });
list[4].Add("3000", new List<string>() { "y" });
list.MergeKeys(2, 4);
Here's how you approach a problem like this. First, specify what you're trying to do.
Given a SortedDictionary<TKey1, SortedDictionary<TKey2, List<TValue>>>
and two keys intoKey
and fromKey
in the dictionary, merge the dictionary with key fromKey
into the dictionary with key intoKey
.
Now specify what it means to merge two dictionaries. Given two dictionaries to
and from
of type SortedDictionary<TKey2, List<TValue>>
to merge them means the following. For each TKey2 key
in from
there are two possiblities:
key
is in to
. In this case add the list from[key]
to the list to[key]
.
key
is not in to
. In this case add key
to to
with value from[key]
.
Then, remove key fromKey
from the dictionary.
Let's translate this to code:
Given a SortedDictionary<TKey1, SortedDictionary<TKey2, List<TValue>>>
and two keys intoKey
and fromKey
in the dictionary
SortedDictionary<TKey2, List<TValue>> to;
SortedDictionary<TKey2, List<TValue>> from;
// check that dictionary has intoKey
if (!dictionary.TryGetValue(intoKey, out to)) {
throw new ArgumentOutOfRangeException("intoKey");
}
// check that dictionary has fromKey
if (!dictionary.TryGetValue(fromKey, out from)) {
throw new ArgumentOutOfRangeException("fromKey");
}
For each TKey2 key
in from
there are two possiblities:
foreach(TKey2 key in from.Keys) {
// key is in to
if (to.Keys.Contains(key)) {
// add the list from[key] to the list to[key]
to[key].AddRange(from[key]);
}
// key is not in to
else {
// add an entry (key, from[key]) to the dictionary
to.Add(key, from[key]);
}
}
Then, remove key fromKey
from the dictionary.
dictionary.Remove(fromKey);
The rest of the code is just error checking