6

I have a list of { string Key, IEnumerable<string> Values } items and want to transform it into a list of { string Key, string Value } items, such that the new list contains n items for each Key.

I want to use LINQ and had the idea to use SelectMany:

list.SelectMany(item => item.Values)

However, as you can see, I lose the Key with that transformation. What's the trick? I guess it should be easy and I am just missing the forest for the trees...

D.R.
  • 20,268
  • 21
  • 102
  • 205
  • 1
    I guess you need to do something like this: https://stackoverflow.com/questions/6428940/how-to-flatten-nested-objects-with-linq-expression – Michael K. Nov 23 '15 at 17:32
  • 6
    `list.SelectMany(item => item.Values, (item, value) => Tuple.Create(item.Key, value))` – user4003407 Nov 23 '15 at 17:32
  • 1
    Yep, forest ... trees ... overloads ... thanks! – D.R. Nov 23 '15 at 17:33
  • Follow up question: is there a possibility to add a `NULL` tuple for each empty values collection? – D.R. Nov 23 '15 at 17:35
  • Currently using `item.Values.Concat(new string[]{null})` - doesn't look very "performancy". – D.R. Nov 23 '15 at 17:37
  • 2
    `item.Values.DefaultIfEmpty()` – user4003407 Nov 23 '15 at 17:39
  • Thanks SO! Response time is amazing! :-) Readers: note that my "solution" has been always adding null entries, while PetSerAl's solution adds null entries only iff the collection is empty. – D.R. Nov 23 '15 at 17:41

2 Answers2

5

I also ran into this brain freeze. Adding the answer by @PetSerAl from the comments:

list.SelectMany(item => item.Values.DefaultIfEmpty(), (item, value) => Tuple.Create(item.Key, value))
Ben Cull
  • 9,434
  • 7
  • 43
  • 38
-2

Not the compiled code but this may answer your question

var finalList=list.SelectMany(item => item).Select(final => new{KeyName=item.Key,Coll=item.Values}).ToList();

Majed
  • 53
  • 8