【问题标题】:Performance: LinqPad and Entity Framework generate different SQL for same Linq request性能:LinqPad 和 Entity Framework 为相同的 Linq 请求生成不同的 SQL
【发布时间】:2012-06-28 01:35:26
【问题描述】:

我想我从 LinqPad 文档了解到它使用与实体框架不同的 linq 到 tsql 转换器。 LinqPad 实际上至少在一种情况下更有效!详情如下:

LinqPad 生成以下简单的 sql 查询:

SELECT [t0].[personId]
FROM [Person] AS [t0]
WHERE (NOT (([t0].[deleted]) = 1)) AND ([t0].[masterPersonId] = @p0)
ORDER BY [t0].[personId] DESC

对于这个 C# linq 代码:

int? state = null;
string realmId = null;
int? reviewerId = null;
bool? deleted = false;
long? parentPersonId = 1275660779659;

var query = from person in Persons
     where 
     (!deleted.HasValue || person.Deleted == deleted) && 
     (!state.HasValue || person.personState == state) &&
     (!parentPersonId.HasValue || person.masterPersonId == parentPersonId) && 
     (realmId == null || person.realmId == realmId) &&
     (reviewerId == null ||(person.reviewerId == reviewerId ))
     orderby person.personId descending
     select person.personId;

所以你可以看到 LinqPad 翻译了上面的 linq 语句,并在参数值为 null 时删除了无关的 sql。不错!

EF 然而 always 生成这个,不管空参数:

SELECT 
[Extent1].[personId] AS [personId]
FROM [dbo].[Person] AS [Extent1]
WHERE (@p__linq__0 IS NULL OR [Extent1].[deleted] = @p__linq__1) AND 
(@p__linq__2 IS NULL OR [Extent1].[personState] = @p__linq__3) AND 
(@p__linq__4 IS NULL OR [Extent1].[masterPersonId] = @p__linq__5) AND 
(@p__linq__6 IS NULL OR [Extent1].[realmId] = @p__linq__7) AND 
((@p__linq__8 IS NULL) OR ([Extent1].[reviewerId] = @p__linq__9))

它使查询速度变慢。我们希望使用 LinqPad 为 EF 评估生成的 sql,但如果结果不同,显然不会。看起来我们可以针对 LinqPad 中的 EF 连接的自定义程序集。我会尝试一下,看看我们是否至少可以将 sql 查询放在一起。

有人曾经走过这条路,或者知道我们可以利用的 EF 设置吗?我们正在运行 EF4。

提前致谢。

【问题讨论】:

  • 我会根据需要编写查询。执行(blah == null || obj.blah == blah),尤其是一遍又一遍,往往会使代码有点模糊,并且确实会导致查询执行计划效率低下(或者我是这样被 DBA 告知的)。我更希望看到var query = .... 后跟if (blah != null) query = query.Where(obj => obj.blah == blah); 形式的组合
  • 是的,这就是我们前进的方向。谢谢安东尼。看起来我可以将 linq 连接定位到我们的 EF 程序集。
  • Linqpad 在您刚连接到数据库时会即时创建一个 linq-to-sql DataContext。所以你看到的是EF和L2S之间的区别。在 SQL 方面,L2S 在多个方面胜过 EF,但反过来也是如此。正如您已经发现的那样,您可以将 Linqpad 连接到您的 EF 上下文以查看 EF 如何翻译 linq 语句。

标签: entity-framework linqpad


【解决方案1】:

我从 LinqPad 的作者那里找到了这个出色的网络广播,他在其中提到了这个问题。 http://oreilly.com/pub/e/1295

我使用的是 Linq To SQL 转换而不是 EF。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-06-22
    • 1970-01-01
    • 2010-09-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多