Entity Framework 与 Include 和 Select 在一起

Entity Framework with Include and Select together

我有以下实体(要保存的伪代码space)

Program [ int Id, 
          string Name, 
          List<ProgramFoodType> ProgramFoodTypes, 
          List<ProgramFood> ProgramFoods]

ProgramFoodType[ int Id, int ProgramId, int Type, bool IsActive]
ProgramFood [ int Id, int ProgramId, Food Food, FoodType FoodType]
Food [int Id, string Name]
FoodType [int Id, string Name]

我的任务是获取单个 Program 及其相关 ProgramFoodTypes 条件 ProgramFoodType 应该是活动的 ProgramFoods 与相关实体 FoodFoodType

到目前为止我使用了以下内容

1- 下面的查询将检索 ProgramFoodTypesProgramFoods 的详细信息,但它会带来所有活动和非活动的 ProgramFoodTypes

var program = mEntities.Programs
                          .Include(p =>p.ProgramFoodTypes)
                          .Include(p =>p.ProgramFoods.Select(f =>f.Food))
                          .InClude(p =>p.ProgramFoods.Select( f =>f.FoodType))
                          .Where(m =>m.Id== Id);

2- 下面的查询将检索详细信息但缺少 FoodFoodType

var program = (from p in mEntities.Programs
              where p.Id ==Id
              select new {
                 Program = p,
                 ProgramFoodTypes = from pf in p.ProgramFoodTypes
                                    where pf.IsActive
                                    select pf,                  
                 ProgramFoods = p.ProgramFoods // here i can't add include statement
              }).ToArray().Select(m => m.Program);

如何在第二个查询中包含食物和食物类型?

试试这个:

var program = mEntities.Programs
                       .Include(p => p.ProgramFoodTypes)
                       .Include(p => p.ProgramFoods.Select(f => f.Food))
                       .InClude(p => p.ProgramFoods.Select(f => f.FoodType))
                       .SingleOrDefault(m => m.Id == Id && m.ProgramFoodTypes.All(t => t.IsActive));

对于你的第二个解决方案,我认为你可以使用:

var program = (from p in mEntities.Programs
                  .Include(p => p.ProgramFoods.Select(f => f.Food))
                  .Include(p => p.ProgramFoods.Select(f => f.FoodType))
               where p.Id == Id
               select new {
                  Program = p,
                  ProgramFoodTypes = from pf in p.ProgramFoodTypes
                                     where pf.IsActive
                                     select pf,                  
                  p.ProgramFoods 
               }).ToArray().Select(m => m.Program);

更新: 由于您在 linq 查询中使用匿名类型,Include statements are dismissed.
您必须在客户端加载所有相关 ProgramFoodTypes,然后进行过滤:

var program = mEntities.Programs
                   .Include(p => p.ProgramFoodTypes)
                   .Include(p => p.ProgramFoods.Select(f => f.Food))
                   .Include(p => p.ProgramFoods.Select(f => f.FoodType))
                   .SingleOrDefault(m => m.Id == Id);

program.ProgramFoodTypes = program.ProgramFoodTypes.Where(pft => pft.IsActive);  

您可以使用 AsNoTracking() 或在新对象中克隆返回的 Program 对象,以确保您的数据在数据库端完好无损。

可能是:

var program = (from p in mEntities.Programs
          where p.Id ==Id
          select new {
             Program = p,
             ProgramFoodTypes = from pf in p.ProgramFoodTypes
                                where pf.IsActive
                                select pf,                  
             ProgramFoods = p.ProgramFoods.Select(y => new {
                 Food = y.Food,
                 Type = y.FoodType
             }) 
          }).ToArray().Select(m => m.Program);