M.R.
M.R.

Reputation: 4827

How do I write this linq inner query?

I want to write a linq query where I want to check each iteration of an inner list. Without linq, this would basically be a nested for loop - like this:

List<Item> selectedList = new List<Item>();
            foreach (Item i in item.Children)
            {
                var childPages = ((from innerItem in i.Children
                                   where innerItem.Template.BaseTemplates.Contains(new TemplateItem(ContextDatabase.GetItem(templateID)), new Compare())
                                   select innerItem).DefaultIfEmpty());

                if (childPages.First() == null)
                {
                    selectedList.AddRange(childPages.ToList());
                }
            }

I converted the inner loop into a linq query - now I want to convert the for loop into the same - is there a way to write this in linq, so that I don't have to have the foeach loop?

Upvotes: 1

Views: 123

Answers (2)

Grant Winney
Grant Winney

Reputation: 66449

I can't see your classes, so this is a best guess. Also, I'm assuming you don't have to create a new instance of TemplateItem and Compare repeatedly inside the LINQ statement.

var templateItem = new TemplateItem(ContextDatabase.GetItem(templateID));
var comparer = new Compare();

selectedList.AddRange(item.Children.SelectMany(
    x => x.Children.Where(y => y.Template.BaseTemplates.Contains(templateItem, comparer))));

(I'm using the method syntax here instead of query syntax, since that's what I'm more familiar with. The results should be the same.)

Upvotes: 1

Matt Tester
Matt Tester

Reputation: 4814

It looks like you're getting an item from the database on each iteration in order to do a comparison ... is that what you absolutely require? There should be an easier way to do the comparisons based on just id's (but would need more information from you I think).

Anyway, to remove the outer foreach, you can do another from clause:

var childPages = (from i in item.Children
                 from innerItem in i.Children
                 where innerItem.Template.BaseTemplates.Contains(new TemplateItem(ContextDatabase.GetItem(templateID)), new Compare())
                 select innerItem).DefaultIfEmpty();

But again, I'd look closely at the need for ContextDatabase.GetItem(templateID)

Upvotes: 1

Related Questions