EF代码优先和分页

EF code first and Paging

我们正在使用 EF 6.1 和代码优先以及工作单元和存储库模式。

我们面临的困惑是,在很多地方都写着如果我们在 Dbset 上使用 Skip & Take,分页会自动处理。 但是当我们看到正在创建的查询时,它不包含任何分页子句。

请问可能是什么情况,示例代码如下:

 public virtual IEnumerable<TEntity> GetSorted(Func<TEntity, Object> order,int skip, int take, params Expression<Func<TEntity, object>>[] includes)
        {
            IQueryable<TEntity> query = dbSet;



            foreach (var include in includes)
            {
                query = dbSet.Include(include);
            }

            IEnumerable<TEntity> data = dbSet.OrderBy(order).Skip(skip).Take(take).ToList();

            //IEnumerable<TEntity> data = query.OrderBy(order).Skip(skip).Take(take).ToList();

            return data;
        }

感谢任何帮助..

您的 order 参数需要是 Expression<Func<TEntity, TSortBy>> 类型才能匹配 Queryable.OrderBy() 的签名。当您传递委托 (Func<TEntity, Object>) 时,唯一匹配此参数的 OrderBy() 重载是 Enumerable.OrderBy() 而不是您期望的 Queryable.OrderBy() (两者都是当然是扩展方法)。

当排序由 Enumerable.OrderBy() (Linq-to-Objects) 完成时,必须首先执行查询(因为 Linq-to-Objects 用于处理已经在内存中的对象) .

但是,当调用 Queryable.OrderBy() 时,order-by 表达式被传递给 Linq 提供程序,然后该提供程序能够解析并将其转换为商店查询(在本例中为 SQL ).

因此,当您将 Func<TEntity, Object> 传递给 OrderBy 时,您会在 return 中获得 IEnumerable<TEntity>,并进一步(链接)调用 Skip()Take() 不再被 Linq-To-Entities 拦截。

您的方法签名应如下所示:

public virtual IEnumerable<TEntity> GetSorted<TSortedBy>(Expression<Func<TEntity, TSortedBy>> order, int skip, int take, params Expression<Func<TEntity, object>>[] includes)

MSDN