Entity Framework: Querying child entities?

Taking your example the following should do what you need. Take a look here for more info db. Entry(Parents) .

Collection("Children") .Query().Cast() . Where(c => c. Age >= 5)) .Load().

Taking your example the following should do what you need. Take a look here for more info. Db.

Entry(Parents) . Collection("Children") .Query().Cast() . Where(c => c.

Age >= 5)) .Load().

Thanks for the reply, but I'm still confused! I've edited my original question to explain why! – ETFairfax Oct 13 at 14:41.

I think parents and child are not really well suited as separate entities. A child can always also be a parent and usually a child has two parents (a father and a mother), so it's not the simplest context. But I assume you just have a simple 1:n relationship as in the following master-slave model that I used.

What you need to do is make a left outer join (that answer has led me on the right path). Such a join is a bit tricky to do, but here's the code var query = from m in ctx. Masters join s in ctx.

Slaves on m. MasterId equals s. MasterId into masterSlaves from ms in masterSlaves.

Where(x => x. Age > 5).DefaultIfEmpty() select new { Master = m, Slave = ms }; foreach (var item in query) { if (item. Slave == null) Console.

WriteLine("{0} owns nobody. ", item.Master. Name); else Console.

WriteLine("{0} owns {1} at age {2}. ", item.Master. Name, item.Slave.Name, item.Slave.

Age); } This will translate to the following SQL statement with EF 4.1 SELECT Extent1. MasterId AS MasterId, Extent1.Name AS Name, Extent2. SlaveId AS SlaveId, Extent2. MasterId AS MasterId1, Extent2.Name AS Name1, Extent2. Age AS Age FROM dbo.

Master AS Extent1 LEFT OUTER JOIN dbo. Slave AS Extent2 ON (Extent1. MasterId = Extent2. MasterId) AND (Extent2. Age > 5) Note that it is important to perform the additional where clause on the age on the joined collection and not between the from and the select.

EDIT: IF you want a hierarchical result you can convert the flat list by performing a grouping: var hierarchical = from line in query group line by line. Master into grouped select new { Master = grouped. Key, Slaves = grouped.

Select(x => x. Slave). Where(x => x!

= null) }; foreach (var elem in hierarchical) { Master master = elem. Master; Console. WriteLine("{0}:", master.

Name); foreach (var s in elem. Slaves) // note that it says elem. Slaves not master.

Slaves here! Console. WriteLine("{0} at {1}", s.

Name, s. Age); } Note that I used an anonymous type to store the hierarchical result. You can of course create also a specific type like this class FilteredResult { public Master Master { get; set; } public IEnumerable Slaves { get; set; } } and then project the group into instances of this class.

That makes it easier if you need to pass these results to other methods.

The only way to get a collection of parents with a filtered children collection in a single database roundtrip is using a projection. It is not possible to use eager loading (Include) because it doesn't support filtering, Include always loads the whole collection. The explicite loading way shown by @Daz requires one roundtrip per parent entity.

Example: var result = db. Parents . Select(p => new { Parent = p, Children = p.Children.

Where(c => c. Age >= 5) }) .ToList(); You can directly work with this collection of anonymous type objects. (You can also project into your own named type instead of an anonymous projection (but not into an entity like Parent).) EF's context will also populate the Children collection of the Parent automatically if you don't disable change tracking (using AsNoTracking() for example).

In this case you can then project the parent out of the anonymous result type (happens in memory, no DB query): var parents = result. Select(a => a. Parent).ToList(); parentsi.

Children will contain your filtered children for each Parent. Edit to your last Edit in the question: I am after a) A list of parents who have a child older than 5 (and include only those children). The code above would return all parents and include only the children with Age >= 5, so potentially also parents with an empty children collection if there are only children with Age = 5: var result = db.

Parents . Where(p => p.Children. Any(c => c.

Age >= 5)) . Select(p => new { Parent = p, Children = p.Children. Where(c => c.

Age >= 5) }) .ToList().

Perhaps if you wrote an example SQL query we could help you convert it to LINQ-Entities.

I cant really gove you an answer,but what I can give you is a way to a solution, that is you have to find the anglde that you relate to or peaks your interest. A good paper is one that people get drawn into because it reaches them ln some way.As for me WW11 to me, I think of the holocaust and the effect it had on the survivors, their families and those who stood by and did nothing until it was too late.

Related Questions