Як об'єднати список списків з однотипними елементами до одного списку елементів?


209

Питання заплутане, але набагато чіткіше, як описано в наступних кодах:

   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 = ???

Не впевнені, чи можливо це за допомогою C # LINQ або Lambda?

По суті, як я зможу об'єднати або " вирівняти " список списків?

Відповіді:


455

Використовуйте метод розширення SelectMany

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

73
Цікаво, скільки людей написали власне розширення "Flatten", не розуміючи, як працює SelectMany?
Джеймс Шек

1
Чому для цього потрібен х => х? Зазвичай я бачу такі речі, як x => x +1, але не x => x.
SwimBikeRun

9
@SwimBikeRun SelectMany використовується для отримання IEnumerable TSources, перетворення кожного TSource у списку в IEnumerable TResults, а потім об'єднання всіх цих IEnumerables в один великий. У цьому випадку у вас є список списків, який слід розпочати, тому, якщо ви хочете об'єднати їх функцією для зіставлення з TSource (який є IEnumerable TResults) в IEnumerable TResults, є функцією ідентичності (x => x). Це дійсно лише особливий випадок, коли вам не потрібен додатковий крок перетворення кожного TSource у список, оскільки це вже список.
Шон

@JaredPar чи можемо ми застосувати цю логіку до списку <список <список <T> >>?
Tk1993

4
@TusharKukreti Звичайно, просто використовуйтеlist.SelectMany(x => x.SelectMany(y => y)).ToList();
Брендон Крамер

13

Ось інтегрована версія синтаксису C #:

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

Трохи заплутано, але приємно. Як це? var items = з позиції в (зі списку в спискуОбрання списку списку) Виберіть пункт
David.Chu.ca

4
"Double from" - це те саме, що SelectMany ... SelectMany - це, мабуть, найпотужніший із методів LINQ (або операторів запитів). Щоб зрозуміти, чому, Google "LINQ SelectMany Monad", і ви дізнаєтесь більше, ніж захочете дізнатися про це.
Річард Ентоні Хайн

3
Не включайте цитати, коли гуглить "LINQ SelectMany Monad", або це просто направить вас сюди.
Оксин

12

Ви це маєте на увазі?

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);

Призводить до: 9 9 9 1 2 3 4 5 6


Або ви можете використовувати list.AddRange () замість Concat (), щоб додати об'єднані елементи до наявного списку.
dahlbyk

1

Для List<List<List<x>>>і так далі, використовувати

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

Це було розміщено в коментарі, але це, на мою думку, заслуговує окремої відповіді.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.