我试图将间接相关实体中的某些内容查询到单一用途的视图模型中。这是我的实体的责备:
public class Team {
[Key]
public int Id { get; set; }
public string Name { get; set; }
public List<Member> Members { get; set; }
}
public class Member {
[Key]
public int Id { get; set; }
public string Name { get; set; }
}
public class Pet {
[Key]
public int Id { get; set; }
public string Name { get; set; }
public Member Member { get; set; }
}
每个类都在我的数据库上下文中的DbSet<T>
。
这是我想从查询构建的视图模型:
public class PetViewModel {
public string Name { get; set; }
public string TeamItIndirectlyBelongsTo { get; set; }
}
我使用此查询执行此操作:
public PetViewModel[] QueryPetViewModel_1(string pattern) {
using (var context = new MyDbContext(connectionString)) {
return context.Pets
.Where(p => p.Name.Contains(pattern))
.ToArray()
.Select(p => new PetViewModel {
Name = p.Name,
TeamItIndirectlyBelongsTo = "TODO",
})
.ToArray();
}
}
但显然还有一个&#34; TODO&#34;在那里。
Gotcha:我目前无法更改实体,因此我无法在{{1}上添加List<Pet>
属性或Team
属性帮帮忙。我想暂时解决查询中的问题。
这是我目前的解决方案:
Member
然而,这有一个&#34; SELECT N + 1&#34;问题在那里。
有没有办法只创建一个 EF查询来获得所需的结果,而无需更改实体?
PS。如果你喜欢&#34;即插即用&#34;包含上述内容的repro,请参阅this gist。
答案 0 :(得分:3)
由于没有提供必要的导航属性,你已经做了很多事情,因为@Evk在评论中提到的不会影响你的数据库结构,但是当你写{{1}时,允许EF提供必要的连接(这里你需要的)。
您的模型的另一个问题是,由于“加入”,您既没有从pet.Member.Team.Name
到Team
,也没有从Pet
到Pet
的导航路径实体Team
没有导航属性。
通过使用现有的导航属性和不常见的Member
运算符,仍然可以通过单个查询获得所需的信息,而不是那么直观:
join