Làm cách nào để hợp nhất danh sách các danh sách với cùng loại mặt hàng vào một danh sách các mặt hàng?


209

Câu hỏi khó hiểu, nhưng rõ ràng hơn nhiều như được mô tả trong các mã sau:

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

Không chắc chắn nếu có thể bằng cách sử dụng C # LINQ hoặc Lambda?

Về cơ bản, làm thế nào tôi có thể nối hoặc " làm phẳng " một danh sách các danh sách?

Câu trả lời:


455

Sử dụng phương thức mở rộng ChọnMany

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

73
Tôi tự hỏi có bao nhiêu người đã viết phần mở rộng "Flatten" của riêng họ mà không nhận ra cách thức hoạt động của SelectMany?
James Schek

1
Tại sao x => x cần thiết để làm việc này? Tôi thường thấy những thứ như x => x +1 nhưng không phải x => x.
BơiBikeRun

9
@SwimBikeRun SelectMany được sử dụng để lấy một số lượng lớn các nguồn, chuyển đổi từng TSource trong danh sách thành một số lượng lớn các lỗi, sau đó ghép tất cả các IEnumerables thành một lớn. Trong trường hợp này, bạn có một danh sách các danh sách để bắt đầu, vì vậy nếu bạn muốn ghép chúng với chức năng để ánh xạ từ một TSource (là một IEnumerable of TResults) sang IEnumerable of TResults là hàm nhận dạng (x => x). Đây thực sự chỉ là một trường hợp đặc biệt khi bạn không cần thêm bước biến mỗi TSource thành một danh sách, vì đó đã là một danh sách.
Sean

@JaredPar chúng ta có thể áp dụng logic này vào danh sách <list <list <T >>> không?
Tk1993

4
@TusharKukreti Chắc chắn, chỉ cần sử dụnglist.SelectMany(x => x.SelectMany(y => y)).ToList();
Brandon Kramer

13

Đây là phiên bản cú pháp tích hợp C #:

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

Một chút bối rối, nhưng tốt đẹp. Làm thế nào điều này? var items = from item in (from list in listOflist select list) select item
David.Chu.ca

4
'Nhân đôi từ' giống với SelectMany ... SelectMany có lẽ là phương thức LINQ mạnh nhất (hoặc toán tử truy vấn). Để biết lý do tại sao, Google "LINQ SelectMany Monad" và bạn sẽ khám phá nhiều hơn những gì bạn muốn biết về nó.
Richard Anthony Hein

3
Không bao gồm các trích dẫn khi googling "LINQ SelectMany Monad" hoặc nó sẽ chỉ dẫn bạn quay lại đây.
Oxin

12

Bạn có hiểu cái này không?

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

Kết quả trong: 9 9 9 1 2 3 4 5 6


Hoặc bạn có thể sử dụng list.AddRange () thay vì Concat () để thêm các mục đã hợp nhất vào danh sách hiện có.
dahlbyk

1

Cho List<List<List<x>>>và như vậy, sử dụng

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

Điều này đã được đăng trong một bình luận, nhưng nó xứng đáng nhận được một câu trả lời riêng theo quan điểm của tôi.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.