我对实体框架有疑问。
如果有人可以解释一下链调用如何在LINQ和Entity Framework之间工作(以及在DB端执行查询的那一点),我将不胜感激。
我想知道在以下两种版本的方法中编写LINQ查询的性能差异(如果有的话):
方法1:
public IEnumerable<T> GetList(Expression<Func<T, bool>> expression, params Expression<Func<T, object>>[] includeProperties)
{
var results = dbSet.Where(expression).AsQueryable().AsNoTracking();
return includeProperties.Aggregate(results, (current, include) => current.Include(include));
}
像这样的函数调用:
GetList(x => x.ID == id);
方法2:
public IEnumerable<T> GetList(params Expression<Func<T, object>>[] includeProperties)
{
var results = dbSet.AsQueryable().AsNoTracking();
return includeProperties.Aggregate(results, (current, include) => current.Include(include));
}
像这样的函数调用:
GetList().Where(x => x.ID == id);
不同之处在于您的例程返回的是IEnumerable<T>
而不是IQueryable<T>
。在第二种情况下,Where将使用IEnumerable的版本而不是IQueryable的版本。“链接”式停止于此(服务器端链停止,而客户端链开始)。在那之后,没有更多更改将对生成的SQL产生任何影响。一旦尝试枚举结果,它将导致所有记录从数据源返回,然后在客户端进行过滤,第一个将在数据源侧进行过滤,因为您在仍是IQueryable的情况下进行了Where操作。
更改例程以返回一个例程IQueryable<T>
,然后在执行和性能方面应该相同。
**旁注,在方法1中,.AsQueryable()是多余的。它已经是一个IQueryable。
这就是我期望这样的函数编写的方式:
public IQueryable<T> GetList(params Expression<Func<T, object>>[] includeProperties)
{
var results = dbSet.AsNoTracking().AsQueryable();
return includeProperties.Aggregate(results, (current, include) => current.Include(include));
}
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句