如何在Linq2Sql中进行递归查询?

时间:2010-10-06 15:42:14

标签: linq-to-sql

我在数据库中有以下表,MenuItems:

ID  ParentID  Name
--- --------- -----
1   0         Item 1
2   1         Item 2
3   1         Item 3
4   0         Item 4
5   3         Item 5

我想编写一个扩展方法,将所有菜单项都放到树的根目录下。像这样:

public IQueryable<MenuItem> GetToRoot(this IQueryable<MenuItem> source, int menuItemID)
{
    return from m in source
           ????
           ????
           select m;
}

如果我使用上面的数据为ID为3的菜单项调用此扩展方法,我应该得到:

ID  ParentID  Name
--- --------- -----
1   0         Item 1
3   1         Item 3

Linq2Sql是否可以只调用一次数据库?

1 个答案:

答案 0 :(得分:1)

我认为你不能在一个查询中做到这一点,这就是我的想法:发现一个项目的父有效需要一个表连接自己。每个附加菜单级别都需要表格与其自身的一次连接。到达根目录需要多少个连接/附加级别?在你执行每一个之前你不会知道,对吗?因此,无论是在数据库/ SQL端还是在LINQ to SQL中,您都必须一次执行每个步骤。

如果您知道您的菜单系统不会超出某个深度,我想您可以设置一个LINQ to SQL查询,该查询将该表与自身连接多次,但这听起来很难看。

我建议在DBML设计器中建立表与自身的关联,这将在类上为您提供父EntityRef<>属性。由于LoadOptions中不允许循环(因此无法预加载父级),因此可以在实体的部分OnLoaded()方法中强制执行父级的延迟加载。

以下是一些相关的SO问题:

https://stackoverflow.com/questions/1435229/hierarchy-problem-replace-recursion-with-linq-join LINQ to SQL for self-referencing tables?

以下是问题的服务器端/ SQL处理:

http://www.sqlteam.com/article/more-trees-hierarchies-in-sql

以下是编写了一些帮助代码的人:

http://www.scip.be/index.php?Page=ArticlesNET18