EF LINQ - Select 仅 parent 实体

EF LINQ - Select only parent Entity

我遇到了一个有趣的问题。

我有一个节点实体。节点可能有也可能没有 Children,也可能有也可能没有 parent.

对于我的 UI,当用户搜索节点时,如果搜索结果同时包含 parent,我只想 return Parent以及它的一个或多个 children(因为 Parent 有一个 Children 导航 属性)。

我搜索包含 "ParentA" 的名称时的结果:

想要的结果:

这是我当前的 LINQ 查询:

var results = await dbContext.Nodes.
                        Include(c => c.Parent).
                        Where(c => c.NodeName.Contains(query)).
                        OrderBy(n => n.NodeName).
                        ToPagedListAsync(page ?? 1, pageSize);

节点实体:

public class Node
{
    [Key, DatabaseGenerated(DatabaseGeneratedOption.None)]
    public long Id { get; set; }

    [Required, MaxLength(50)]
    [DisplayName("Node Name")]
    public string NodeName { get; set; }

    [ForeignKey("Parent")]
    public Nullable<long> ParentId { get; set; }
    public virtual Node Parent { get; set; }

    public virtual ICollection<Node> Children { get; set; }
}

您可以像这样使用 Any 方法:c.Children.Any(x => x.NodeName.Contains(query))

var results = await dbContext.Nodes.
                        Include(c => c.Parent).
                        Where(c => c.NodeName.Contains(query)).
                        Where(c => c.Children.Any(x => x.NodeName.Contains(query))).
                        OrderBy(n => n.NodeName).
                        ToPagedListAsync(page ?? 1, pageSize);

您不需要包含 parent,您可以搜索 children 和 return 以及 parent。如果你需要,你也可以return children。

dbContext.Nodes.Where(
     n =>n.NodeName.Contains(query)) || n.Children.Any(
         c=>c.NodeName.Contains(query))).
                    OrderBy(n => n.NodeName).
                    ToPagedListAsync(page ?? 1, pageSize);

请试试这个....

dbContext.Nodes
     .Where(c => c.NodeName.Contains(query))
     .Select(c=>GetParentOrSelf(c,query))
     .OrderBy(n => n.NodeName)
     .ToPagedListAsync(page ?? 1, pageSize);    


private Node GetParentOrSelf(Node n)
{
    if (n.Parent==null)
        return n;
    else
    {
        if (n.Parent.NodeName.Contains(query))
            return GetParentOrSelf(n.Parent,query);
        else
            return n;
    }
}