IQueryable 和 IEnumerable

其实,对于上面的即有过虑又有排序的条件查询Linq语句,EF是读取数据库中整个Books表中的数据到内存,还是根据Linq查询语句智能的生成SQL再执行查询,完全编码者来决定的。我们打开BookShop.Domain工程的BookRepository类文件,请注意该类中Books属性的返回类型:

  1. ...
  2. public IQueryable<Book> Books {
  3. get { return context.Books; }
  4. }

上篇博文中,我们对使用IQueryable作为返回类型提了个疑问:为什么用IQueryable而不用IEnumerable作为返回类型?答案是:使用IQueryable,EF会根据调用者的Linq表达式先生成相应的SQL查询语句,然后到数据库中执行查询,查询出来的数据即是用户想要的数据;而使用IEnumerable,Linq表达式的过滤、排序等操作都是在内存中发生的,即EF会先从数据库中把整个表的数据查询出来放在内存中,然后由调用者使用Linq语句进行过滤、排序等操作。是不是这样呢?我们来监视一下两种情况EF生成的SQL语句就知道了。

我们先来看看使用IQueryable的情况。重新运行一下程序,然后使用SQL Server Management Studio的活动和监视器查看一下我们的BookShop应用程序所执行的SQL语句,结果如下:

结果证明使用IQueryable,EF是先根据Linq表达式生成相应的SQL语句再执行查询的。

我们再稍稍修改一下代码来看看用IEnumerable的情况。把BookRepository类修改如下:

  1. public class BookRepository : IBookRepository {
  2. private EFDbContext context = new EFDbContext();
  3.  
  4. public IEnumerable<Book> Books {
  5. get { return context.Books; }
  6. }
  7. }

当然BookRepository类所实现的IBookRepository接口(在BookShop.Domain工程的Abstract文件夹中)也要改一下:

  1. public interface IBookRepository {
  2. IEnumerable<Book> Books { get; }
  3. }

再重新运行一下应用程序,用活动和监视器查看最后执行的SQL语句如下图:

我们看到改用IEnumerable后,EF生成的SQL没有任何过滤、排序等的操作,它一次把表中的所有数据都Select出来,和上面写的Linq表达式一点都没关系。

IQueryable虽然可以很智能地根据Linq表达式生成相应的SQL语句,但毕竟有一个分析Linq表达式的过程,相对来说性能比IEnumerable要差。那么我们什么时候用IEnumerable,什么时候用IQueryable呢?我想,对于少量的数据(比如从数据库中读取应用程序相关的系统信息)和不需要对数据进行过滤操作的情况,用IEnumerable比较适合;对于数据量较大需要对数据进行过滤(比如分页查询)的情况,则用IQueryable比较合适。

IQueryable 和 IEnumerable的更多相关文章

  1. IQueryable和IEnumerable,IList的区别

    IQueryable和IEnumerable都是延时执行(Deferred Execution)的,而IList是即时执行(Eager Execution) IQueryable和IEnumerabl ...

  2. C# IQueryable和IEnumerable的区别

    在使用EF查询数据的时候,我们常用的查询数据方式有linq to sql,linq to object, 查询返回的结果有两种类型:IQueryable.IEnumerable,两者内部的处理机制是完 ...

  3. C#编程之IList<T>、List<T>、ArrayList、IList, ICollection、IEnumerable、IEnumerator、IQueryable 和 IEnumerable的区别

    额...今天看了半天Ilist<T>和List<T>的区别,然后惊奇的发现使用IList<T>还是List<T>对我的项目来说没有区别...  在C#中 ...

  4. IQueryable和IEnumerable

    使用EF你必须知道这两个的区别,可以帮助我们的提升性能. 表达树:Linq 表达 ①IQueryable和IEnumerable IQueryable 延时执行:扩展方法接受的是Expression( ...

  5. IQueryable和IEnumerable以及AsEnumerable()和ToList()的区别

    注意:本文背景为 Linq to sql .文中ie指代IEnumerable,iq指代IQueryable. IQueryable 和 IEnumerable 的区别 IQueryable 延时执行 ...

  6. C#中IQueryable和IEnumerable的区别

    最近的一个面试中,被问到IQueryable 和 IEnumerable的区别, 我自己看了一些文章,总结如下: 1. 要明白一点,IQueryable接口是继承自IEnumerable的接口的. 2 ...

  7. C# IEnumerable与IQueryable ,IEnumerable与IList ,LINQ理解Var和IEnumerable

    原文:https://www.cnblogs.com/WinHEC/articles/understanding-var-and-ienumerable-with-linq.html 使用LINQ从数 ...

  8. IQueryable 和 IEnumerable(二)

    IQueryable 和 IEnumerable的扩展方法 一  我们从ef的DbSet<T>看起来,我们看到他继承了IQueryable<T> 和 IEnumerable&l ...

  9. Linq 的IQueryable和IEnumerable方式

    IEnumerable方式: public IEnumerable<WebManageUsers> GetWebManageUsers(ISpecification<WebManag ...

随机推荐

  1. glibc-2.19 之 strlen 实现

    前几天遇到一个有意思的问题,实现strlen 不考虑线程安全: 下面是我的实现: size_t strlen(const char* s) { const char* p = s; while (*p ...

  2. ORACLE表建立自增列

    create tablespace studentDBdatafile 'E:\datafiles_1.dbf' size 10m; create user Huang_Ying_Boidentifi ...

  3. SQL计算年代差

    1.用datediff函数 select datediff(yyyy,StuBirthday,getdate())>17 2.用year函数 select (year(getdate()-yea ...

  4. c#多选下拉框(ComboBox)

    代码如下 using System; using System.Collections.Generic; using System.ComponentModel; using System.Drawi ...

  5. CodeForces Round

    CodeForces Round 199 Div2   完了,这次做扯了,做的时候有点发烧,居然只做出来一道题,差点被绿. My submissions     # When Who Problem ...

  6. 该死的类型转换For input string: "[Ljava.lang.String;@1352dda"

    今天又遇见了这个该死的问题,还是记下来备忘. 从map里取值的时候,将OBJECT对象 先转换成String 然后转换成integer报错 java.lang.NumberFormatExceptio ...

  7. ThreadPool&ManualResetEvent

    在多线程的程序中,经常会出现两种情况: 一种情况: 应用程序中,线程把大部分的时间花费在等待状态,等待某个事件发生,然后才能给予响应 这一般使用ThreadPool(线程池)来解决: 另一种情况:线程 ...

  8. iOS 开发之协议-代理传值

    刚开始做iOS开发的时候,对 protocol.delegate 的理解一直都是晕晕乎乎一知半解的状态,不知道两个UIViewController之间怎么进行传值. 面试过几个童鞋,问道怎么用 del ...

  9. PHP生成缩略图函数

    function img_create_small($big_img, $width, $height, $small_img) { // 大图文件地址,缩略宽,缩略高,小图地址$imgage = g ...

  10. Python2 中文编码处理

    今天写了几个脚本,都遇到了中英文混编的情况.需求要将其中的中文标点符号切换为英文符号. 举个例子: tags = '你好,good, 国语' 要将其中的中文半角逗号替换为英文逗号,为了方便后续的处理 ...