zoukankan      html  css  js  c++  java
  • EF 中 IEnumberable<> 和 IQueryable的区别

    首先一点: IQueryable interface 继承自 IEnumberable interface , 所以 IEnumberable 能做的 IQueryable 都能做;

    共同点: 

      1、两者都是延迟加载(Lazy Loading) , 

      2、EF 使用中共同的方法: where() , skip() ,  OrderbyDescending() , Take() etc ,

        以上这些方法都有两个版本:

          IEnumberable 版本:   Where(Func<Customer, bool> predicate)      

          IQueryable 版本:  Where(Expression<Func<Customer, bool>> predicate) 

                     其中 Expression对象的Compile() 执行后  为 Func<>类型

      3、. AsEnumerable() 方法 使用IEnumberalbe接口, .AsQueryable() 使用IQueryable接口 

    不同点:

      1、IQueryable 允许 LINQ-to-SQL ,  转化成的sql 语句在服务器端执行 

          2、IEnumberable 允许 LINQ-to-Object, 不允许转化成SQL,   只能操作内存中的数据;

    下面通过代码说明:

    1、使用EF中IEnumberable 接口的方法 where()  执行过滤 Empid=2的 Employess 

    EmpEntities ent = new EmpEntities();
    IEnumerable<Employee> emp = ent.Employees; 
    IEnumerable<Employee> temp = emp.Where(x => x.Empid == 2).ToList<Employee>();

    这个操作 生成的SQL语句是: 

    SELECT * FROM [dbo].[ Employees]          /// 获取所有的 Employees

    执行过程是: 从数据库中获取所有的 Employees 到客户端(内存)中, 在内存中执行过滤操作(where()方法)。  

    执行过程如下图示:

    从上可以看出: 这种 查询 方法时比较慢, 因为查询出了所有的数据;

    2、 使用EF 中 IQueryable interface的方法 .where() 执行相同的操作;

    EmpEntities ent = new EmpEntities();
    IQueryable<Employee> emp = ent.Employees;
    IQueryable<Employee> temp =  emp.Where(x => x.Empid == 2).ToList<Employee>();

    生成的SQL语句使: 

    SELECT TOP 1 * FROM [dbo].[ Employees] WHERE [Empid] =10 

    执行过程如下图所示:

    这种执行方式, 通过成的SQL语句 , 在服务器端 执行过滤操作, 然后将符合条件的数据返回客户端(内存中), 而不是将所有的数据都返回到客户端, 

    总结:

    过滤内存中的数据 IEnumberable 接口的方法随时可以使用;

    查询数据库IQueryable 接口的方法,是一个比较好的选择,但是IQueryable接口方法中 使用LINQ语句, 会有一些语句不识别, 比如 自定义方法, 识别都是能够转化成sql语句的方法;

    使用EF , 效率问题是必须要注意的问题,尤其是查询数据,很容造成 n+1问题 、 返回所有数据问题 , 造成查询效率低下;

    PS:  上面图示部分来自 参考资料

    What is the difference between IQueryable<T> and IEnumerable<T>?

    Returning IEnumerable<T> vs. IQueryable<T>

    英文版的 技术资料 真的很齐全, 做技术方面还是要多读英文资料;

  • 相关阅读:
    vue里面的v-for列表循环
    浅谈Vue.use
    js 限制输入框只能输入数字的问题
    vue computed的执行问题
    前端 html 篇
    函数声明 及 名称问题
    文件读写操作
    异常以及异常处理框架探析
    使用JDBC插入数据到ORACLE,使用标识列自增列
    session超时跃出iframe并跳到登陆页面(转载)
  • 原文地址:https://www.cnblogs.com/generalLi/p/6909216.html
Copyright © 2011-2022 走看看