分享使用Entity Framework的一个坑:Include无效

简介:

如果不想延迟加载,可以通过设置:context.Configuration.LazyLoadingEnabled = false;或查询时加上AsNoTracking()方法即可。

如果不想生成代理,可以通过设置:context.Configuration.ProxyCreationEnabled = false;

注意当context.Configuration.ProxyCreationEnabled = false;时延迟加载也就不生效,原理很简单,因为没有代理。

当禁用延迟加载后,关联属性(导航属性)不会被实例化,这时如果需要实例化该属性,则需要通过Include方法,意为显式加载(也有人称为饥饿加载),具体的用法也可参见我之前的文章:http://www.cnblogs.com/zuowj/p/4514230.html

好了有了上面知识的了解,我们想实现一次性加载所有内容包含关联属性的值,且不要生成代理对象,就很简单了,我项目中的语句如下:

1
2
3
4
5
var  context =  new  LocalDbEntities();
context.Configuration.LazyLoadingEnabled =  false ;
context.Configuration.ProxyCreationEnabled =  false ;
result=context.Set<TA_CWTransferRequestInfo>().Where(t =>  true ).Include(t => t.TA_CWBankAccountInfo).GroupBy(t => t.TA_CWBankAccountInfo.bkcode)
         .ToDictionary(gp => gp.Key, gp => gp.ToList());

代码简单说明一下,TA_CWTransferRequestInfo有一个关联属性TA_CWBankAccountInfo,我想实现依据TA_CWBankAccountInfo.bkcode来分组并存入Dictionary中,最后我需要用到TA_CWTransferRequestInfo.TA_CWBankAccountInfo属性的信息,原本以为没有问题,但实际使用时,却报错:无法对 null 引用执行运行时绑定,经DEBUG时发现TA_CWTransferRequestInfo.TA_CWBankAccountInfo=null,这就有点不解了,明明我使用了Include,为何没有加载呢?不解之余查看了一下上述LINQ生成的SQL语句如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
SELECT
     [Project2].[C1]  AS  [C1],
     [Project2].[bkcode]  AS  [bkcode],
     [Project2].[C2]  AS  [C2],
     [Project2].[id]  AS  [id],
     [Project2].[fromactacn]  AS  [fromactacn],
     [Project2].[toactacn]  AS  [toactacn],
     [Project2].[toibkn]  AS  [toibkn],
     [Project2].[toname]  AS  [toname],
     [Project2].[toaddr]  AS  [toaddr],
     [Project2].[tobknm]  AS  [tobknm],
     [Project2].[tobkcode]  AS  [tobkcode],
     [Project2].[trnamt]  AS  [trnamt],
     [Project2].[trncur]  AS  [trncur],
     [Project2].[priolv]  AS  [priolv],
     [Project2].[furinfo]  AS  [furinfo],
     [Project2].[trfdate]  AS  [trfdate],
     [Project2].[trftime]  AS  [trftime],
     [Project2].[comacn]  AS  [comacn],
     [Project2].[field1]  AS  [field1],
     [Project2].[field2]  AS  [field2],
     [Project2].[field3]  AS  [field3],
     [Project2].[field4]  AS  [field4],
     [Project2].[field5]  AS  [field5],
     [Project2].[field6]  AS  [field6],
     [Project2].[field7]  AS  [field7],
     [Project2].[field8]  AS  [field8],
     [Project2].[processing]  AS  [processing],
     [Project2].[transtype]  AS  [transtype],
     [Project2].[trfmode]  AS  [trfmode],
     [Project2].[createdt]  AS  [createdt],
     [Project2].[lastupdatedt]  AS  [lastupdatedt],
     [Project2].[lastrspid]  AS  [lastrspid],
     [Project2].[rowversion]  AS  [rowversion],
     [Project2].[lyd_guid]  AS  [lyd_guid]
     FROM  SELECT
         [Distinct1].[bkcode]  AS  [bkcode],
         AS  [C1],
         [Join2].[id]  AS  [id],
         [Join2].[fromactacn]  AS  [fromactacn],
         [Join2].[toactacn]  AS  [toactacn],
         [Join2].[toibkn]  AS  [toibkn],
         [Join2].[toname]  AS  [toname],
         [Join2].[toaddr]  AS  [toaddr],
         [Join2].[tobknm]  AS  [tobknm],
         [Join2].[tobkcode]  AS  [tobkcode],
         [Join2].[trnamt]  AS  [trnamt],
         [Join2].[trncur1]  AS  [trncur],
         [Join2].[priolv]  AS  [priolv],
         [Join2].[furinfo]  AS  [furinfo],
         [Join2].[trfdate]  AS  [trfdate],
         [Join2].[trftime]  AS  [trftime],
         [Join2].[comacn]  AS  [comacn],
         [Join2].[field11]  AS  [field1],
         [Join2].[field21]  AS  [field2],
         [Join2].[field31]  AS  [field3],
         [Join2].[field41]  AS  [field4],
         [Join2].[field51]  AS  [field5],
         [Join2].[field6]  AS  [field6],
         [Join2].[field7]  AS  [field7],
         [Join2].[field8]  AS  [field8],
         [Join2].[processing]  AS  [processing],
         [Join2].[transtype]  AS  [transtype],
         [Join2].[trfmode]  AS  [trfmode],
         [Join2].[createdt]  AS  [createdt],
         [Join2].[lastupdatedt1]  AS  [lastupdatedt],
         [Join2].[lastrspid]  AS  [lastrspid],
         [Join2].[rowversion1]  AS  [rowversion],
         [Join2].[lyd_guid]  AS  [lyd_guid],
         CASE  WHEN  ([Join2].[priolv]  IS  NULL THEN  CAST ( NULL  AS  int ELSE  END  AS  [C2]
         FROM    ( SELECT  DISTINCT
             [Extent2].[bkcode]  AS  [bkcode]
             FROM   [dbo].[TA_CWTransferRequestInfo]  AS  [Extent1]
             INNER  JOIN  [dbo].[TA_CWBankAccountInfo]  AS  [Extent2]  ON  [Extent1].[fromactacn] = [Extent2].[actacn] )  AS  [Distinct1]
         LEFT  OUTER  JOIN   ( SELECT  [Extent3].[id]  AS  [id], [Extent3].[fromactacn]  AS  [fromactacn], [Extent3].[toactacn]  AS  [toactacn], [Extent3].[toibkn]  AS  [toibkn], [Extent3].[toname]  AS  [toname], [Extent3].[toaddr]  AS  [toaddr], [Extent3].[tobknm]  AS  [tobknm], [Extent3].[tobkcode]  AS  [tobkcode], [Extent3].[trnamt]  AS  [trnamt], [Extent3].[trncur]  AS  [trncur1], [Extent3].[priolv]  AS  [priolv], [Extent3].[furinfo]  AS  [furinfo], [Extent3].[trfdate]  AS  [trfdate], [Extent3].[trftime]  AS  [trftime], [Extent3].[comacn]  AS  [comacn], [Extent3].[field1]  AS  [field11], [Extent3].[field2]  AS  [field21], [Extent3].[field3]  AS  [field31], [Extent3].[field4]  AS  [field41], [Extent3].[field5]  AS  [field51], [Extent3].[field6]  AS  [field6], [Extent3].[field7]  AS  [field7], [Extent3].[field8]  AS  [field8], [Extent3].[processing]  AS  [processing], [Extent3].[transtype]  AS  [transtype], [Extent3].[trfmode]  AS  [trfmode], [Extent3].[createdt]  AS  [createdt], [Extent3].[lastupdatedt]  AS  [lastupdatedt1], [Extent3].[lastrspid]  AS  [lastrspid], [Extent3].[rowversion]  AS  [rowversion1], [Extent3].[lyd_guid]  AS  [lyd_guid], [Extent4].[bkcode]  AS  [bkcode]
             FROM   [dbo].[TA_CWTransferRequestInfo]  AS  [Extent3]
             INNER  JOIN  [dbo].[TA_CWBankAccountInfo]  AS  [Extent4]  ON  [Extent3].[fromactacn] = [Extent4].[actacn] )  AS  [Join2]  ON  ([Distinct1].[bkcode] = [Join2].[bkcode])  OR  (1 = 0)
     )   AS  [Project2]
     ORDER  BY  [Project2].[bkcode]  ASC , [Project2].[C2]  ASC

看到这个SQL语句我也是醉了,与我的本意完全不同,从上面的SQL语句可以看出来:它虽然关联时有用到[TA_CWBankAccountInfo],但最后只查出[TA_CWTransferRequestInfo]的字段,当然也就无法实例化关联的TA_CWBankAccountInfo属性了,最后得出结论,当使用GroupBy+ToDictionary时,Include方法无效。

鉴于上述结论,我将上述语句稍微作了一下调整,就成功通过测试了,更改后的语句:

1
2
3
4
5
var  context =  new  LocalDbEntities();
context.Configuration.LazyLoadingEnabled =  false ;
context.Configuration.ProxyCreationEnabled =  false ;
return  context.Set<TA_CWTransferRequestInfo>().Where(t =>  true ).Include(t => t.TA_CWBankAccountInfo).ToList().GroupBy(t => t.TA_CWBankAccountInfo.bkcode)
         .ToDictionary(gp => gp.Key, gp => gp.ToList());

发现区别了没有?我只是在Include后加了一个ToList()方法就可以了,目的是先从数据库查询出符合条件的数据(包含关联的数据),然后再在本地进行GroupBy操作,可以看一下生成的SQL语句:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
SELECT
     [Extent1].[priolv]  AS  [priolv],
     [Extent1].[id]  AS  [id],
     [Extent1].[fromactacn]  AS  [fromactacn],
     [Extent1].[toactacn]  AS  [toactacn],
     [Extent1].[toibkn]  AS  [toibkn],
     [Extent1].[toname]  AS  [toname],
     [Extent1].[toaddr]  AS  [toaddr],
     [Extent1].[tobknm]  AS  [tobknm],
     [Extent1].[tobkcode]  AS  [tobkcode],
     [Extent1].[trnamt]  AS  [trnamt],
     [Extent1].[trncur]  AS  [trncur],
     [Extent1].[furinfo]  AS  [furinfo],
     [Extent1].[trfdate]  AS  [trfdate],
     [Extent1].[trftime]  AS  [trftime],
     [Extent1].[comacn]  AS  [comacn],
     [Extent1].[field1]  AS  [field1],
     [Extent1].[field2]  AS  [field2],
     [Extent1].[field3]  AS  [field3],
     [Extent1].[field4]  AS  [field4],
     [Extent1].[field5]  AS  [field5],
     [Extent1].[field6]  AS  [field6],
     [Extent1].[field7]  AS  [field7],
     [Extent1].[field8]  AS  [field8],
     [Extent1].[processing]  AS  [processing],
     [Extent1].[transtype]  AS  [transtype],
     [Extent1].[trfmode]  AS  [trfmode],
     [Extent1].[createdt]  AS  [createdt],
     [Extent1].[lastupdatedt]  AS  [lastupdatedt],
     [Extent1].[lastrspid]  AS  [lastrspid],
     [Extent1].[rowversion]  AS  [rowversion],
     [Extent1].[lyd_guid]  AS  [lyd_guid],
     [Extent2].[actacn]  AS  [actacn],
     [Extent2].[ibknum]  AS  [ibknum],
     [Extent2].[actnam]  AS  [actnam],
     [Extent2].[bknm]  AS  [bknm],
     [Extent2].[bkcode]  AS  [bkcode],
     [Extent2].[addr]  AS  [addr],
     [Extent2].[actacnas]  AS  [actacnas],
     [Extent2].[trncur]  AS  [trncur1],
     [Extent2].[field1]  AS  [field11],
     [Extent2].[field2]  AS  [field21],
     [Extent2].[field3]  AS  [field31],
     [Extent2].[field4]  AS  [field41],
     [Extent2].[field5]  AS  [field51],
     [Extent2].[lastupdatedt]  AS  [lastupdatedt1],
     [Extent2].[rowversion]  AS  [rowversion1]
     FROM   [dbo].[TA_CWTransferRequestInfo]  AS  [Extent1]
     INNER  JOIN  [dbo].[TA_CWBankAccountInfo]  AS  [Extent2]  ON  [Extent1].[fromactacn] = [Extent2].[actacn]

这个SQL语句是既简洁又明了,符合我的意图,从遇到的这个坑得到启示,有时不要把问题复杂化,换个角度看问题或许能找到更好的解决办法。

本文转自 梦在旅途 博客园博客,原文链接:http://www.cnblogs.com/zuowj/p/5102548.html  ,如需转载请自行联系原作者

相关文章
|
3天前
|
云安全 数据采集 人工智能
古茗联名引爆全网,阿里云三层防护助力对抗黑产
阿里云三层校验+风险识别,为古茗每一杯奶茶保驾护航!
古茗联名引爆全网,阿里云三层防护助力对抗黑产
|
3天前
|
存储 机器学习/深度学习 人工智能
大模型微调技术:LoRA原理与实践
本文深入解析大语言模型微调中的关键技术——低秩自适应(LoRA)。通过分析全参数微调的计算瓶颈,详细阐述LoRA的数学原理、实现机制和优势特点。文章包含完整的PyTorch实现代码、性能对比实验以及实际应用场景,为开发者提供高效微调大模型的实践指南。
495 1
kde
|
3天前
|
人工智能 关系型数据库 PostgreSQL
n8n Docker 部署手册
n8n是一款开源工作流自动化平台,支持低代码与可编程模式,集成400+服务节点,原生支持AI与API连接,可自托管部署,助力团队构建安全高效的自动化流程。
kde
332 3
|
3天前
|
存储 人工智能 Java
AI 超级智能体全栈项目阶段四:学术分析 AI 项目 RAG 落地指南:基于 Spring AI 的本地与阿里云知识库实践
本文介绍RAG(检索增强生成)技术,结合Spring AI与本地及云知识库实现学术分析AI应用,利用阿里云Qwen-Plus模型提升回答准确性与可信度。
226 91
AI 超级智能体全栈项目阶段四:学术分析 AI 项目 RAG 落地指南:基于 Spring AI 的本地与阿里云知识库实践
|
4天前
|
传感器 人工智能 算法
数字孪生智慧水务系统,三维立体平台,沃思智能
智慧水务系统融合物联网、数字孪生与AI技术,实现供水全流程智能监测、预测性维护与动态优化。通过实时数据采集与三维建模,提升漏损控制、节能降耗与应急响应能力,推动水务管理从经验驱动迈向数据驱动,助力城市水资源精细化、可持续化管理。
282 143
|
18天前
|
存储 关系型数据库 分布式数据库
PostgreSQL 18 发布,快来 PolarDB 尝鲜!
PostgreSQL 18 发布,PolarDB for PostgreSQL 全面兼容。新版本支持异步I/O、UUIDv7、虚拟生成列、逻辑复制增强及OAuth认证,显著提升性能与安全。PolarDB-PG 18 支持存算分离架构,融合海量弹性存储与极致计算性能,搭配丰富插件生态,为企业提供高效、稳定、灵活的云数据库解决方案,助力企业数字化转型如虎添翼!
|
7天前
|
人工智能 移动开发 自然语言处理
阿里云百炼产品月刊【2025年9月】
本月通义千问模型大升级,新增多模态、语音、视频生成等高性能模型,支持图文理解、端到端视频生成。官网改版上线全新体验中心,推出高代码应用与智能体多模态知识融合,RAG能力增强,助力企业高效部署AI应用。
353 1