rmamedov
rmamedov

Reputation: 150

Use LINQ to find value inside a nested collection

I have the following snippet of code that I'd like to convert to LINQ. The goal is to find a match in the inner collection and return its Data property. Any suggestions?

    string data = null;
    foreach (var section in sections)
    {
        foreach (var field in section.Fields)
        {
            if (field.Id == id)
            {
                data = field.Data;
            }
        }
    }

Upvotes: 1

Views: 3052

Answers (2)

DavidG
DavidG

Reputation: 118947

You can use SelectMany to flatten the collection then flter it with a Where

var matches = sections
    .SelectMany(s => s.Fields)
    .Where(f => f.Id == id)
    .Select(f => f.Data);

Now matches contains all the data strings that match. If you only have a single match, you can use Single (or SingleOrDefault if there may not be any) to get that individual value. If you might have more matches, use FirstOrDefault or LastOrDefault. (in your code, Last is the method that will give you the same answer)

You could put all that together and simplify:

data = sections
    .SelectMany(s => s.Fields)
    .SingleOrDefault(f => f.Id == id)
    ?.Data;

Note the ? just in case you have no matches.

Upvotes: 5

Paul Raff
Paul Raff

Reputation: 346

The following code would work, based on Rob's comment:

sections.SelectMany(x => x.Fields).Where(field => field.Id == id).Select(field => field.Data).FirstOrDefault()

Upvotes: 0

Related Questions