gpt4 book ai didi

c# - 如何使用单个 SQL 生成的查询在 EFCore 中选择模拟多对多的属性

转载 作者:行者123 更新时间:2023-11-30 20:26:37 28 4
gpt4 key购买 nike

EFCore 在不创建链接实体的情况下不支持多对多关系。我需要从一对多对一关系的“另一端”有效地选择一部分属性。

我发誓这已经有了答案,但还没有找到。

使用这些模型:

public class Book
{
public int BookId { get; set; }
public string Title { get; set; }
public Author Author { get; set; }
public ICollection<BookCategory> BookCategories { get; set; }
}

public class Category
{
public int CategoryId { get; set; }
public string CategoryName { get; set; }
public string ExtraProperties {get; set; }
public ICollection<BookCategory> BookCategories { get; set; }
}

public class BookCategory
{
public int BookId { get; set; }
public Book Book { get; set; }
public int CategoryId { get; set; }
public Category Category { get; set; }
}

这个问题是标题为“Select specific properties from include ones in entity framework core”的类似但不同的问题的扩展

我正在寻找返回 List<string> categoryNames 的查询本书的类别。

这个嵌套的选择,使用“投影”导致多个 SQL 查询:

var result= await _ctx.Books
.Where(x => x.BookId == id)
.Select(x => x.BookCategorys
.Select(y => y.Category.CategoryName )
.ToList())
.FirstOrDefaultAsync();

任何带有 .Include(x => x.BookCategory).ThenInclude(x => Category) 的解决方案将在应用选择之前从服务器加载所有数据。

是否有符合以下条件的查询?

  • 只生成 1 个 SQL 查询
  • 不加载整个链接实体和/或整个导航属性 2 个“跃点”。
  • 仅返回 List<string>类别名称。

我由此推断Entity Framework Core generates two select queries for one-to-many relationship , 这是不可能的。

最佳答案

一般情况下,你无法控制生成的SQL以及ORM执行了多少SQL查询。在撰写本文时,EF Core(版本 2.0.2)已知会在查询包含集合投影时生成 N + 1 个查询。这is fixed in the next 2.1 release ,但仍会生成并执行至少 2 个查询。

但每条规则都有异常(exception)。由于您希望返回一个相关的集合投影,您可以简单地使用SelectMany而不是原来的Select + FirstOrDefault构造。这些就相当于这个场景,EF Core 还不够聪明,不能像对待前者一样对待后者。考虑到需要考虑多少其他情况,这是可以理解的。好处是,以这种方式重写 LINQ 查询会生成所需的单个 SQL 查询转换:

var result = await _ctx.Books
.Where(x => x.BookId == id)
.SelectMany(x => x.BookCategorys
.Select(y => y.Category.CategoryName))
.ToListAsync();

关于c# - 如何使用单个 SQL 生成的查询在 EFCore 中选择模拟多对多的属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49616571/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com