【发布时间】:2013-07-05 23:19:27
【问题描述】:
假设我们在数据模型中有四个实体:Categories、Books、Authors 和 BookPages。还假设 Categories-Books、Books-Authors 和 Books-BookPages 关系是一对多的。
如果从数据库中检索到类别实体实例——包括“Books”、“Books.BookPages”和“Books.Authors”——这将成为一个严重的性能问题。此外,不包括它们会导致“对象引用未设置为对象的实例”异常。
使用多个 Include 方法调用的最佳做法是什么?
- 编写单个方法 GetCategoryById 并在其中包含所有项目(性能问题)
- 编写单个方法 GetCategoryById 并发送要包含的关系列表(也许,但似乎仍然不够优雅)
- 编写 GetCategoryByIdWithBooks、GetCategoryByIdWithBooksAndBooksPages 和 GetCategoryByIdWithBooksAndAuthors 等方法(不实用)
编辑:第二个选项我的意思是这样的:
public static Category GetCategoryById(ModelEntities db, int categoryId, params string[] includeFields)
{
var categories = db.Categories;
foreach (string includeField in includeFields)
{
categories = categories.Include(includeField);
}
return categories.SingleOrDefault(i => i.CategoryId == categoryId);
}
调用时我们需要这样的代码:
Category theCategory1 = CategoryHelper.GetCategoryById(db, 5, "Books");
Category theCategory2 = CategoryHelper.GetCategoryById(db, 5, "Books", "Books.Pages");
Category theCategory3 = CategoryHelper.GetCategoryById(db, 5, "Books", "Books.Authors");
Category theCategory4 = CategoryHelper.GetCategoryById(db, 5, "Books", "Books.Pages", "Books.Authors");
这种方法有什么明显的缺点吗?
【问题讨论】:
-
您能否详细说明为什么会出现这种异常?延迟加载对您不起作用吗?
-
如您所知,当他不使用 Include 方法时会出现此异常。延迟加载当然可以,但是使用 Include 的目的是什么? Entity Framework 可能默认包含所有关系,并且由于延迟加载,相关实体在调用时会被加载。在这种情况下,使用 Include 没有任何意义。我可能遗漏了什么,我很好奇那是什么。
-
你不应该得到一个空引用。你用过 virtual 关键字吗?您还应该在构造函数中将导航集合设置为空列表。 Include 的目的是告诉实体框架您想要预先加载实体而不是延迟加载。启用延迟加载时,EF 默认不包含所有引用
-
@Colin 我应该在哪里使用 virtual 关键字?您写了“启用延迟加载时...”。我们可以启用/禁用此功能吗?如果可以,如何启用?
标签: c# entity-framework architecture data-access-layer ef-database-first