如何防止Entity Framework加载所有子对象

时间:2016-07-16 23:49:28

标签: c# .net asp.net-mvc entity-framework linq

我目前正在使用Entity Framework使用ASP.NET MVC构建论坛 我有3个主要模型 [类别] 1 - * [论坛] 1 - * [发布]

如果我有5个类别,每个人有4个论坛,每个论坛有1000个帖子 我想只显示类别,当我这样做时,这意味着我也选择了20000个帖子?

因为每个类别对象都有列表<'论坛>> ,并且每个论坛对象都有列表与LT;'邮政'> 由于映射和关系

4 个答案:

答案 0 :(得分:3)

您可以使用延迟加载来阻止检索子对象。见here。默认情况下应启用延迟加载。

延迟加载是在第一次访问引用实体/实体的属性时从数据库自动加载实体或实体集合的过程。

使用POCO实体类型时,通过创建派生代理类型的实例然后覆盖虚拟属性以添加加载挂钩来实现延迟加载。例如,当使用下面定义的Blog实体类时,将在第一次访问Posts导航属性时加载相关的Posts:

public virtual ICollection<Post> Posts { get; set; } 

您可以使用.Include()来实现特定的预先加载。 例如:

db.Forums.Include(i => i.Posts)

答案 1 :(得分:1)

使用存储的SQL过程仅显示有问题的类别。我假设经常使用此功能,因此会影响性能。 SP是预编译的,执行计划是已知的,另外你可以从aFewTablesnJoins中添加一个select distinct categoryfield,其中someId = @参数在你的类别查询中 - Less IO,admin对性能更满意。 当然,如上所述,懒惰实例化总是一种选择。

答案 2 :(得分:0)

好的,我找到了这个例子,它使用Explicit Loading和IN运算符。代码如下所示:

  

(依赖实体,有FK TutorId)[课程] N - &gt; -------- 1 [Tutor]   (主要实体)

     

(依赖实体,有FK SubjectId)[课程] N - &gt; ----- 1 [主题](主要实体)

// get all courses 
IEnumerable<Course> courses = context.Courses.ToList(); 
// select tutor ids from courses (C# logic, without DB access)
IEnumerable<int> tutorIds = courses.Select(c => c.TutorId);
// select subject ids from courses (C# logic, without DB access)
IEnumerable<int> subjectIds = courses.Select(c => c.SubjectId); 

context.Tutors.Where( t => tutorIds.Contains(t.TutorId) ).Load();
context.Subjects.Where( s => subjectIds.Contains(s.SubjectId) ).Load();

这似乎应该有效,但我需要对它进行测试并给出一个提示,如果它对我有效。

答案 3 :(得分:0)

在dbcontext文件中设置lazyloading=false