301

The question is confusing, but it is much more clear as described by the following code:

   List<List<T>> listOfList;
   // add three lists of List<T> to listOfList, for example
   /* listOfList = new {
        { 1, 2, 3}, // list 1 of 1, 3, and 3
        { 4, 5, 6}, // list 2
        { 7, 8, 9}  // list 3
        };
   */
   List<T> list = null;
   // how to merger all the items in listOfList to list?
   // { 1, 2, 3, 4, 5, 6, 7, 8, 9 } // one list
   // list = ???

Not sure if it possible by using C# LINQ or Lambda?

Essentially, how can I concatenate or "flatten" a list of lists?

0

4 Answers 4

638

Use the SelectMany extension method

list = listOfList.SelectMany(x => x).ToList();
Sign up to request clarification or add additional context in comments.

5 Comments

I wonder how many folks have written their own "Flatten" extension not realizing how SelectMany works?
Why is x => x needed for this to work? I usually see things like x = > x +1 but not x = > x.
@SwimBikeRun SelectMany is used to take an IEnumerable of TSources, convert each TSource in the list into an IEnumerable of TResults, then concatenate all those IEnumerables into one big one. In this case you have a list of lists to start, so if you want to concatenate them the function to map from a TSource (which is an IEnumerable of TResults) to an IEnumerable of TResults is the identity function (x => x). This is really just a special case where you don't need the extra step of turning each TSource into a list, because it's already a list.
@JaredPar can we apply this logic to list<list<list<T>>> ?
@TusharKukreti Sure, just use list.SelectMany(x => x.SelectMany(y => y)).ToList();
16

Here's the C# integrated syntax version:

var items =
    from list in listOfList
    from item in list
    select item;

3 Comments

Little bit confusing, but nice. How this? var items = from item in (from list in listOflist select list) select item
The 'double from' is the same as SelectMany ... SelectMany is probably the most powerful of the LINQ methods (or query operators). To see why, Google "LINQ SelectMany Monad" and you'll discover more than you'll want to know about it.
Don't include the quotes when googling "LINQ SelectMany Monad" or it'll just direct you back to here.
16

For List<List<List<x>>> and so on, use

list.SelectMany(x => x.SelectMany(y => y)).ToList();

This has been posted in a comment, but it deserves a separate answer in my opinion.

Comments

15

Do you mean this?

var listOfList = new List<List<int>>() {
    new List<int>() { 1, 2 },
    new List<int>() { 3, 4 },
    new List<int>() { 5, 6 }
};
var list = new List<int> { 9, 9, 9 };
var result = list.Concat(listOfList.SelectMany(x => x));

foreach (var x in result) Console.WriteLine(x);

Results in: 9 9 9 1 2 3 4 5 6

1 Comment

Or you could use list.AddRange() instead of Concat() to add the merged items to the existing list.

Your Answer

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.