对象-关系映射框架比如EF有三种 方式使用 模型中的导航属性来加载关联数据。

一、.Lazy Loading.(关联数据在访问导航属性时被透明的加载,不需要特别的代码,自动的加载)

当一个实体第一次读取的时候,关联数据不会被检索。然后,当你第一次访问这个实体的导航属性的时候,导航属性需要的数据自动的被检索。每当你第一次从导航属性获取数据时,都会向数据库发送查询。这样,会导致多个查询被发送到数据库。一个是实体本身,另外,每当实体的关联数据第一次被访问的时候。EF6.x的DbContext类默认启用了Lazy loading.

lazy loading 不支持AsNoTracking()方法,使用了.AsNoTracking(),lazy loading会发生异常。

而EF Core1的版本是不支持Lzay Loading的。从EF2.1.开始支持Lazy Loading,但必须是可以覆写的导航属性,也就是 说定义为虚 virtual属性,和能够被继承的。需要进行以下设置。

1、安装代理类

PMC:Install-Package Microsoft.EntityFrameworkCore.Proxies -Version 2.1.1

在Startup.cs配置文件中,ConfigureService方法中,

//启动文件,在依赖注入容器中注册数据库上下文对象。
2、services.AddDbContext<SchoolContext>(options =>
options.UseLazyLoadingProxies().UseSqlServer(Configuration.GetConnectionString("DefaultConnection"))); //如果未在Context中添加UseLazyLoadingProxies,导航属性不会添加。

departments =context.Departments;

foreach(Department d in departments)

{

foreach(Course c in d.Courses)

{

courseLIst.Add(d.Name + c.title)

}

}

二、EagerLoading  (关联数据在初始的查询里面就从数据库加载)

当实体第一次被读取的时候,关联的数据一起被检索。这将会导致仅有的连接查询会检索所有需要的全部数据。通过EF core使用Include方法和ThenInclude方法来指定eagerLoding.

departments =context.Departments.Include(x =>x.Course) //一条语句就从数据库中加载所有的关联属性。

foreach(Department d in departments)

{

foreach(Course c in d.Courses)

{

courseList.Add(d.Name +c.Title);

}

}

三、Explicit loading (关联数据后来才能被显式的从数据库加载)

1.这个与lazy loading相似,除了需要显式的使用代码来检索关联数据。当你访问一个导航属性的时候,不会自动发生。需要通过对象状态管理器(object state manager)Entry手动的加载关联数据,,调用Collection.Load(导航属性为集合)方法和reference.Load(导航属性为单个实体)方法。你使用显式加载仅仅是关闭了lazy loading。

departments =context.Departments.Tolist();

foreach(Department d in departments)

{

context.Entry(d).Collection(d =>d.Courses).Load(); //用Entry load()代码明确从数据库加载关联数据。

foreach(Course c in d.Courses)

{

courseList.Add(d.Name +c.Title);

}

}

2.你能够使用单独的查询来检索数据,EF会 修复导航属性。也就是说EF自动地将它们所属的单独检索的实体添加到先前检索实体集的导航属性中。对于检索相关数据的查询,可使用Load方法而不是返回列表或对象的方法,例如:ToList()或者 Single()

departments =context.Departments.Include(x =>x.Courses)

foreach(Department d in departments)

{

context.Courses.Where(c =>c.DepartmentID == d.DepartmentId).Load(); //从数据库中加载实体的导航属性,使用load();

foreach(Course c in d.Courses) // 由于EF  Core修复了导航属性,因此,这里不是lazy loading,而是eager loading.

{

courseList.Add(d.Name +c.Title)

}

}

因为lazy loading和explicit loading不会立即查询属性值,因为它们都属于延迟加载(deferred loading).

性能考虑

如果每一个实体的导航属性都需要被查询,eager  loading通常能提供最好的性能,因为只有一个查询被发送到数据库,比起检索单个实体的独立的查询,减少了对数据库访问来回的次数,显得更加高效。

另一方面,在一些情况下,Lazy loading更加高效。Eager loading可能导致非常复杂的连接查询,SQL服务器不能有效的处理。如果你仅仅需要访问一个实体集的其中一部分(子集)实体的导航属性,则延迟加载可能会执行得更好,因为预先加载将检索比您需要的更多数据。 如果性能至关重要,最好以两种方式测试性能,以便做出最佳选择。

延迟加载可以掩盖导致性能问题的代码。例如,处理大量的实体,并且在每次迭代中使用了多个导航属性,没有指定eager loading或explicit loading ,这样的代码执行效率非常低。因为多次往返数据库。一个应用程序在本地开发过程中运行良好,但当移植到Azure SQL数据库时,由于延迟增加和Lazying loading可能出现性能问题。

序列化 的时候使用lazy loading将导致失控的链式反应,序列化之前要关闭lazy loading.

读取关联数据(EF Core2.1.1)的更多相关文章

  1. Contoso 大学 - 5 – 读取关联数据

    原文 Contoso 大学 - 5 – 读取关联数据 By Tom Dykstra, Tom Dykstra is a Senior Programming Writer on Microsoft's ...

  2. EF学习笔记(七):读取关联数据

    总目录:ASP.NET MVC5 及 EF6 学习笔记 - (目录整理) 本篇参考原文链接:Reading Related Data 本章主要讲述加载显示关联数据: 数据加载分为以下三种 Lazy l ...

  3. 【EF6学习笔记】(七)读取关联数据

    本篇参考原文链接:Reading Related Data 本章主要讲述加载显示关联数据: 数据加载分为以下三种 Lazy loading 这种加载方式在于需要用到这个导航属性数据的时候,才会去数据库 ...

  4. EF学习笔记(八):更新关联数据

    学习笔记主目录链接:ASP.NET MVC5 及 EF6 学习笔记 - (目录整理) 上一篇链接:EF学习笔记(七):读取关联数据 本篇原文链接:Updating Related Data 本篇主要考 ...

  5. 【EF6学习笔记】(八)更新关联数据

    上一篇链接:EF学习笔记(七):读取关联数据 本篇原文链接:Updating Related Data 本篇主要考虑对于有关联的数据进行新增.删除.更新操作:比如Course .Instructor: ...

  6. EF里单个实体的增查改删以及主从表关联数据的各种增删 改查

    本文目录 EF对单个实体的增查改删 增加单个实体 查询单个实体 修改单个实体 删除单个实体 EF里主从表关联数据的各种增删改查 增加(增加从表数据.增加主从表数据) 查询(根据主表找从表数据.根据从表 ...

  7. ASP.NET MVC + EF 利用存储过程读取大数据,1亿数据测试很OK

    看到本文的标题,相信你会忍不住进来看看! 没错,本文要讲的就是这个重量级的东西,这个不仅仅支持单表查询,更能支持连接查询, 加入一个表10W数据,另一个表也是10万数据,当你用linq建立一个连接查询 ...

  8. ASP.NET MVC + EF 利用存储过程读取大数据

    ASP.NET MVC + EF 利用存储过程读取大数据,1亿数据测试很OK 看到本文的标题,相信你会忍不住进来看看! 没错,本文要讲的就是这个重量级的东西,这个不仅仅支持单表查询,更能支持连接查询, ...

  9. EF+LINQ事物处理 C# 使用NLog记录日志入门操作 ASP.NET MVC多语言 仿微软网站效果(转) 详解C#特性和反射(一) c# API接受图片文件以Base64格式上传图片 .NET读取json数据并绑定到对象

    EF+LINQ事物处理   在使用EF的情况下,怎么进行事务的处理,来减少数据操作时的失误,比如重复插入数据等等这些问题,这都是经常会遇到的一些问题 但是如果是我有多个站点,然后存在同类型的角色去操作 ...

随机推荐

  1. Django-extra的用法

    ## select提供简单数据 # SELECT age, (age > 18) as is_adult FROM myapp_person; Person.objects.all().extr ...

  2. 车牌识别--OMAP4430处理器上測试

    OMAP4430(ME865) arm-linux-gcc 4.5.1(FriendlyARM) 软浮点执行结果: root@lj:/workspace/carid# arm-linux-gcc ca ...

  3. iOS学习之iOS沙盒(sandbox)机制和文件操作1

    iOS学习之iOS沙盒(sandbox)机制和文件操作 接上篇 iOS学习之iOS沙盒(sandbox)机制和文件操作(一) 我们看看如何获取应用程序沙盒目录.包括真机的沙盒的目录. 1.获取程序的H ...

  4. python发送post请求上传文件,无法解析上传的文件

    前言 近日,在做接口测试时遇到一个奇葩的问题. 使用post请求直接通过接口上传文件,无法识别文件. 遇到的问题 以下是抓包得到的信息: 以上请求是通过Postman直接发送请求的. 在这里可以看到消 ...

  5. mnesia练习及基本操作

    Mnesia基本用法 查看表结构 查看mnesia表的结构: mnesia:info(). 查看此表的基本信息: mnesia:table_info(<tableName>, all). ...

  6. OpenCV 入门示例之一:显示图像

    前言 本文展示一个显示图像的示例程序,它用于从硬盘加载一副图像并在屏幕上显示. 代码示例 // 此头文件包含图像IO函数的声明 #include "highgui.h" int m ...

  7. 搭建React Native开发环境

    搭建React Native开发环境 本文档是Mac下搭建的环境,针对的目标平台不同,以及开发 iOS 和 Android 的不同,环境搭建也有差异. Github地址:https://github. ...

  8. springboot中tomcat找不到jsp页面【转载】

    这个原理还没搞明白,只知道是内嵌的tomcat找jsp时默认不读取resources目录,但是具体的默认读取的是哪个目录,打了一下午断点我也没找到.... 修改方式,添加配置修改tomcat的读取目录 ...

  9. java手写单例模式

    1 懒汉模式 public class Singleton { private Singleton singleton = null; private Singleton() { } public S ...

  10. vue web开发

    https://www.szzhdj.gov.cn/js/pagejs/assemblyHall_dzs1.js https://www.szzhdj.gov.cn/js/pagejs/assembl ...