【问题标题】:Self-referencing tables in Linq2SqlLinq2Sql 中的自引用表
【发布时间】:2010-09-18 19:49:34
【问题描述】:

我已经看到很多关于 Linq2Sql 中的自引用表以及如何为特定根对象急切加载所有子记录的问题。我通过访问所有底层属性实现了一个临时解决方案,但是您可以看到这对性能没有任何好处。

问题是,所有记录都使用关联 GUID 相互关联。示例如下:

RootElement
- Id: 1
- ParentId: null
- CorrelationId: 4D68E512-4B55-44f4-BA5A-174B630A03DD

ChildElement1
- Id: 2
- ParentId: 1
- CorrelationId: 4D68E512-4B55-44f4-BA5A-174B630A03DD

ChildElement2
- Id: 3
- ParentId: 2
- CorrelationId: 4D68E512-4B55-44f4-BA5A-174B630A03DD

ChildElement1
- Id: 4
- ParentId: 2
- CorrelationId: 4D68E512-4B55-44f4-BA5A-174B630A03DD

在我的例子中,我确实可以访问correlationId,所以我可以通过执行以下查询来检索我的所有记录:

from element in db.Elements
where element.CorrelationId == '4D68E512-4B55-44f4-BA5A-174B630A03DD'
select element;

但是,当然,我希望通过执行以下查询将这些元素相互关联:

from element in db.Elements
where element.CorrelationId == '4D68E512-4B55-44f4-BA5A-174B630A03DD' && element.ParentId == null
select element;

我的问题是:是否可以将第一个查询的结果组合为某种“缓存机制”,用于获取根元素的查询?

感谢您的意见。

J.

【问题讨论】:

    标签: c# linq-to-sql


    【解决方案1】:

    我不太清楚您要做什么,或者您所说的“缓存机制”是什么意思。第二个查询如何创建任何类型的关联?

    我的第一个预感是您想按父级对结果进行分组,在这种情况下,您只需在第一个查询的结果上调用 GroupBy(x => x.ParentId)

    我的第二个预感是,您的第二个查询是只获取根元素,在这种情况下,您只需在第一个查询的结果上调用 Where(x => x.ParentId == null)

    如果这不是您要查找的内容,请进一步说明。

    编辑:

    针对您的第一条评论,以下是执行这两个查询的方法:

    var correlated_elements = db.Elements.Where(element => element.CollelationId == '4D68E512-4B55-44f4-BA5A-174B630A03DD');
    var root_elements = correlated_elements.Where(element => element.ParentId == null);
    

    这只会对数据库进行一次查询。尽管如此,您的第二个查询并没有创建层次结构——它只是返回没有ParentId 的元素。如果您可以描述所需的层次结构,我们可以通过查询来实现它。

    如果您不确定实际对数据库执行了哪些查询,可以将 SQL 输出到控制台或使用LINQ-to-SQL Profiler 的试用版。

    【讨论】:

    • “缓存机制”是指我想在第二个查询中使用第一个查询的结果。在第一个查询中,我得到了具有相同 CorrelationId 的所有项目的非分层列表。如果我可以使用这些数据来填充查询 2 的层次结构,而 Linq 不必在每次访问子属性时懒惰地获取数据,那就太好了。有什么想法吗?
    • 好的,谢谢杰。我确实测试了你描述的场景,虽然它只生成一个查询,但我仍然 - 就像你说的那样 - 在我的结构中没有得到层次结构。我猜这是合乎逻辑的。问题是我不知道我的层次结构会有多深。这就是为什么我希望 Linq 在默认情况下急切地加载所有子元素,而不必自己传递它们。我感觉这在技术上是不可能的。知道这种自引用递归是否可以在 Entity Framework (3.5-4.0) 中工作?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多