c# - 如何在不在根级别加载子项的情况下加载递归实体?

标签 c# linq entity-framework-core

如果您查看 CoreUI live demo website ,您会在左侧看到一个导航栏,其中包含多个可折叠级别。我想动态地实现这样的东西。我创建了一个简单的类:

public class NavItem
{
    [Key]
    [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
    public int navItemId { get; set; }
    public int sortOrder { get; set; }
    public bool isTitle { get; set; }
    public bool isDivider { get; set; }
    public string cssClass { get; set; }
    public string name { get; set; }
    public string url { get; set; }
    public string icon { get; set; }
    public string variant { get; set; }
    public string badgeText { get; set; }
    public string badgeVariant { get; set; }
    public virtual ICollection<NavItem> children { get; set; }
}

注意 ICollection<NavItem> children属性(property)。

无论如何,我用示例数据集(CoreUI 示例)填充了它,它正确地保存在数据库中,其中一个名为 NavItemId1 的字段存储了所有子项的父项 ID。到目前为止一切都很好。

现在我想查询它,所以我做了显而易见的事情:

var nI = db.navItems.ToList();

这相当出色地生成了一个包含所有导航项的列表,带有 children在需要时正确填充子项的属性。

但是,它也包含根级别的所有子项目...所以我有 40 个而不是 15 个根级别项目。

是否有一个我可以运行的 linq 查询,它可以防止列表的根级别被子项填满(即排除字段 NavItemId1 != null 的任何地方),但仍能正确加载结构的其余部分?

例如这是我现在得到的:

  • root1
  • root2
    • root2 的 child 1
    • root2 的 child2
      • root2 的 child1-of-child2
  • root3
    • 根的 child 1 <-- I want my list to end here
  • root2 的 child
  • root2 的 child2
    • root2 的 child1 的 child2
  • root2 的 child1 的 child2
  • root3 的 child 1

我可以添加 isRoot bool 属性,然后运行读取后查询以删除根级别没有 isRoot 的任何项目设置,例如

var nI = db.navItems.ToList();
nI = nI.Where(p => p.isRoot).ToList();

但这看起来很笨拙。

显示问题的示例代码。特别要看第 6 项和第 16 项(第 1 个有 1 个级别的 child ,第 2 个有 2 个级别)。

https://github.com/adev73/EFCore-LoadParentWithChildren-Example

最佳答案

你得到的结果是正确的。您请求所有 navItems 作为一个列表,您将获得一个包含所有 navItems 的列表。子节点的修复是 EF 为您提供的一个很好的“奖励”。

您还正确地将过滤器应用于实例化列表而不是直接应用于数据集。如果您将它应用于数据集,您的子节点将不会被填充!然后,要填充您必须使用 Includes 的子节点,但这只会让您达到 1 级,这可能还不够……当然您可以添加多个 include,但这不会很好地扩展……

你做这件事的“笨拙”方式毕竟看起来并不那么笨拙..我觉得它相当优雅。

关于c# - 如何在不在根级别加载子项的情况下加载递归实体?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50613110/

相关文章:

c# - 如何在客户端调试我的应用程序 exe

C#:将 0xFFFFFFFF 分配给 int

c# - LINQ to Dynamics CRM 在本地查询过滤记录

c# - ECONNRESET 在 CreatedAtAction 之后,使用 _context.AddRange() - EF 2.0

c# - 实体类型 'ModeratedUser'需要定义主键

c# - 动态数据透视 Linq C#

c# - 我可以在 ASP.NET 中使用 C# 获取时间参数的本地化缩写吗?

c# - Linq 连接查询 - 如何在 View MVC C# 中显示新表

linq - 成对分组项目

c# - EF 可以使用影子属性制作多列索引吗?