c# – 带有标量结果的LINQ是否会触发延迟加载
我阅读了Entity Framework团队的
Loading Related Entities帖子,并对最后一段感到有些困惑:
using (var context = new BloggingContext()) { var blog = context.Blogs.Find(1); // Count how many posts the blog has var postCount = context.Entry(blog) .Collection(b => b.Posts) .Query() .Count(); } 为什么这里需要查询计数方法? var blog = context.Blogs.Find(1); var postCount = blog.Posts.Count(); 是否会触发延迟加载并且所有集合都将被加载到内存中,而不是我会得到我想要的标量值? 解决方法
第一种方法是不加载所有行,因为从IQueryable调用Count方法,但第二种方法是加载所有行,因为它是从ICollection调用的.
我做了一些测试来验证它.我用Table1和Table2测试了它,其中Table1具有PK“Id”并且Table2具有FK“Id1”(1:N).我从这里使用了EF profiler http://efprof.com/. 第一种方法: var t1 = context.Table1.Find(1); var count1 = context.Entry(t1) .Collection(t => t.Table2) .Query() .Count(); 否选择*来自表2: SELECT TOP (2) [Extent1].[Id] AS [Id] FROM [dbo].[Table1] AS [Extent1] WHERE [Extent1].[Id] = 1 /* @p0 */ SELECT [GroupBy1].[A1] AS [C1] FROM (SELECT COUNT(1) AS [A1] FROM [dbo].[Table2] AS [Extent1] WHERE [Extent1].[Id1] = 1 /* @EntityKeyValue1 */) AS [GroupBy1] 第二种方法: var t1 = context.Table1.Find(1); var count2 = t1.Table2.Count(); 表2加载到内存中: SELECT TOP (2) [Extent1].[Id] AS [Id] FROM [dbo].[Table1] AS [Extent1] WHERE [Extent1].[Id] = 1 /* @p0 */ SELECT [Extent1].[Id] AS [Id],[Extent1].[Id1] AS [Id1] FROM [dbo].[Table2] AS [Extent1] WHERE [Extent1].[Id1] = 1 /* @EntityKeyValue1 */ 为什么会这样? Collection(t => t.Table2)的结果是一个实现ICollection的类,但它没有加载所有行,并且有一个名为IsLoaded的属性. Query方法的结果是IQueryable,这允许调用Count而不预加载行. t1.Table2的结果是ICollection,它正在加载所有行以获取计数.顺便说一句,即使您只使用t1.Table2而不要求计数,行也会被加载到内存中. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |