代码之家  ›  专栏  ›  技术社区  ›  thatismatt

linq2sql中的EntitySet与表查询性能

  •  9
  • thatismatt  · 技术社区  · 17 年前

    在Linq to SQL类中,为什么从外键创建属性 EntitySet 对象,实现 IEnumerable ,其中作为对象 DataContext Table 实现的对象 IQueryable ?

    编辑: 为了澄清这一点,这里有一个例子说明了我试图理解的内容。这个例子:

    ctx.Matches.Where(x => x.MatchID == 1).Single()
               .MatchPlayers.Max(x => x.Score);
    

    两次命中数据库,其中:

    ctx.MatchPlayers.Where(x => x.MatchID == 1)
                    .Max(x => x.Score);
    

    只运行1个查询。以下是痕迹:

    exec sp_executesql N'SELECT [t0].[MatchID], [t0].[Date]
    FROM [dbo].[Matches] AS [t0]
    WHERE [t0].[MatchID] = @p0',N'@p0 int',@p0=1
    go
    exec sp_executesql N'SELECT [t0].[MatchID], [t0].[PlayerID], [t0].[Score]
    FROM [dbo].[MatchPlayers] AS [t0]
    WHERE [t0].[MatchID] = @p0',N'@p0 int',@p0=1
    go
    

    exec sp_executesql N'SELECT MAX([t0].[Score]) AS [value]
    FROM [dbo].[MatchPlayers] AS [t0]
    WHERE [t0].[MatchID] = @p0',N'@p0 int',@p0=1
    go
    

    这也表明,更糟糕的是,最大值是在C级别而不是在数据库中完成的。

    我知道发生这种情况的原因是 可查询的 S和 可枚举的 S,那为什么 MatchPlayers 第一个示例中的对象实现 可查询的 接口以获得与后一个示例相同的好处。

    3 回复  |  直到 13 年前
        1
  •  1
  •   Jon Skeet    17 年前

    表实际上是一个概念性的问题——它们确实存在于服务器上,因此您需要查询以获取条目。外键条目实际上是由另一个查询获取的,因此在这一点上它们是本地可用的。这是一个相当模糊的描述,但希望它能超越一般的概念。

        2
  •  3
  •   Amy B    17 年前
    ctx.Matches.Where(x => x.MatchID == 1).Single()
    

    single()返回匹配项,而不是IQueryable(match)。

    只需将single()推到最后一步:

    ctx.Matches
      .Where(m => m.MatchID == 1)
      .Select(m => m.MatchPlayers.Max(mp => mp.Score))
      .Single();
    

    这个查询显示,可以在查询中使用matchplayers属性。它解决了我对提问者问题的解释——“为什么我不能在查询中使用EntitySet?”你可以。

        3
  •  0
  •   Jaecen    17 年前

    这是 addressed on the MSDN forums . 推理的要点是,在对数据库进行查询时,很难跟踪添加和删除的对象。相反,EntitySet是您可以操作的相关对象的本地副本。不幸的是,正如您注意到的,这有一个副作用,即将表达式转移到对象调用的LINQ中,而不是性能更好的LINQ到SQL。

    推荐文章