Entity Framework 是不是支持 COUNT(*) OVER()

Posted

技术标签:

【中文标题】Entity Framework 是不是支持 COUNT(*) OVER()【英文标题】:Does Entity Framework support COUNT(*) OVER()Entity Framework 是否支持 COUNT(*) OVER() 【发布时间】:2018-02-28 15:00:57 【问题描述】:

简介

就像与 nhibernate 相关的 this question 一样,我想知道 Entity Framework 6 是否存在类似的东西。我做了一些研究,但没有发现任何可用的东西。

除了使用.Skip(x).Take(y) 查询分页结果之外,我们还希望在应用分页之前获取与我们的where 子句 匹配的所有项目的计数。

我们现在将应用了 where 子句的 LINQ 查询放在一个变量中,因此我们可以使用它两次,一次获取计数,一次获取分页结果。 p>

但出于性能原因,我们希望在一个查询中同时执行这两项操作,就像在 RAW SQL 查询中使用 COUNT(*) OVER() 一样。

问题

实体框架是否以某种方式支持COUNT(*) OVER()?如果没有,您能否指点一下从哪里开始寻找实现这一点。

提案

首先我想创建一个IQueryable<T> 扩展方法:CountOver(out long totalCount),但这可能行不通,因为我们仍在构建查询。

然后我考虑引入一个属性[CountOver],我们可以在我们的实体模型中使用它:

public class Person

    public string Fullname  get; set; 
    [CountOver]
    public long TotalCount  get; set; 

如果我们可以修改源代码,后者将不会那么难实现,但目前我不知道这是否可能......

【问题讨论】:

【参考方案1】:

没有。 LINQ 没有从概念上转换为 COUNT() OVER() 的查询运算符。但是你可以重复使用一个查询来 Count() 它的行,并选择它的结果。

例如,类似

        var q = db. . . ;

        var q2 = from r in q
                 select new  r, count = q.Count() ;

【讨论】:

似乎转换为 CROSS JOIN 并使用 +/- 相同的子查询两次。知道这如何影响 MSSQL 2016 的性能吗? YMMV,不过应该差不多吧。 刚刚用 LINQPad 测试过,比分别运行 q.Count()q.Skip(x).Take(y) 慢 33%。 我希望单独运行 Count() 比两种组合查询形式更好(或不差)。

以上是关于Entity Framework 是不是支持 COUNT(*) OVER()的主要内容,如果未能解决你的问题,请参考以下文章

Entity Framework 4 ste删除外键关系

Mysql 该如何 Entity Framework 数据库迁移 和 如何更好的支持EntityFramework.Extended

在Oracle中使用Entity Framework 6 CodeFirst

Entity Framework Extended Library (EF扩展类库,支持批量更新删除合并多个查询等)

Entity Framework 7 支持批量操作和 JSON 列

Entity Framework 4 表值函数