Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

LINQ: How to get items from an inner list into one list?

Tags:

c#

list

linq

Having the following classes (highly simplified):

public class Child {     public string Label;     public int CategoryNumber;     public int StorageId; }  public class Parent {     public string Label;     public List<Child> Children = new List<Child>(); } 

And having the following data:

var parents = new List<Parent>();  var parent = new Parent() {Label="P1"}; parent.Children.Add(new Child() {Label="C1", CategoryNumber=1, StorageId=10}); parent.Children.Add(new Child() {Label="C2", CategoryNumber=2, StorageId=20}); parents.Add(parent);  parent = new Parent() {Label="P2"}; parent.Children.Add(new Child() {Label="C3", CategoryNumber=1, StorageId=10}); parent.Children.Add(new Child() {Label="C4", CategoryNumber=2, StorageId=30}); parents.Add(parent);  parent = new Parent() {Label="P3"}; parent.Children.Add(new Child() {Label="C5", CategoryNumber=3, StorageId=10}); parent.Children.Add(new Child() {Label="C6", CategoryNumber=2, StorageId=40}); parents.Add(parent); 

Now, how would I get a list of children (with CategoryNumber=2) from the list of parents containing at least one child with CategoryNumber = 1 ?

I can do the following but it does not appear to be optimal:

var validParents = from p in parents                    where p.Children.Any (c => c.CategoryNumber==1)                    select p; var selectedChildren = validParents.Select(p => from c in p.Children                                                  where c.CategoryNumber == 2                                                 select c); 

Here's what I get for selectedChildren:

  • IEnumerable<IEnumerable<Child>>
    • IEnumerable<Child>
      • C2 2 20
    • IEnumerable<Child>
      • C4 2 30

Is it possible to only have one flat list containing the two children elements instead of two sub-list? How would it translate in LINQ ?

like image 902
Stécy Avatar asked Jun 22 '09 17:06

Stécy


People also ask

What is difference between select and SelectMany in LINQ?

Select and SelectMany are projection operators. A select operator is used to select value from a collection and SelectMany operator is used to selecting values from a collection of collection i.e. nested collection.

What is SelectMany in LINQ C#?

The SelectMany in LINQ is used to project each element of a sequence to an IEnumerable<T> and then flatten the resulting sequences into one sequence. That means the SelectMany operator combines the records from a sequence of results and then converts it into one result.

What is any () in LINQ?

The Any operator is used to check whether any element in the sequence or collection satisfy the given condition. If one or more element satisfies the given condition, then it will return true. If any element does not satisfy the given condition, then it will return false.


1 Answers

You can string a couple queries together, using SelectMany and Where.

var selectedChildren = (from p in parents                        where p.Children.Any (c => c.CategoryNumber==1)                        select p)                        .SelectMany(p => p.Children)                        .Where(c => c.CategoryNumber == 2);  // or...  var selectedChildren = parents                          .Where(p => p.Children.Any(c => c.CategoryNumber == 1))                          .SelectMany(p => p.Children)                          .Where(c => c.CategoryNumber == 2); 
like image 86
Scott Ivey Avatar answered Oct 06 '22 13:10

Scott Ivey