C# 选择整个表时返回空参数的Linq查询
我对Linq很陌生,但最近我一直在使用它,并且信心不断增强。我使用EF通过MVC项目中的上下文访问数据库 在这个实例中,我要做的就是从我的一个表中获取所有数据C# 选择整个表时返回空参数的Linq查询,c#,asp.net-mvc,linq,entity-framework,C#,Asp.net Mvc,Linq,Entity Framework,我对Linq很陌生,但最近我一直在使用它,并且信心不断增强。我使用EF通过MVC项目中的上下文访问数据库 在这个实例中,我要做的就是从我的一个表中获取所有数据 var msgs = context.Messages.ToList(); 我觉得这很好,但是当我以后使用列表时: foreach(Message m in msgs) { var info = context.Contacts.Where(x => x.Id == m.recipient.Id)
var msgs = context.Messages.ToList();
我觉得这很好,但是当我以后使用列表时:
foreach(Message m in msgs)
{
var info = context.Contacts.Where(x => x.Id == m.recipient.Id)
.Select(x => x.MobileNumber).FirstOrDefault();
}
消息对象有一个必需的收件人
,它是一个联系人对象(我数据库中的另一个实体)
我在上面一行得到一个NullArgumentException
,因为消息对象的收件人参数在我的列表中为null,尽管它们在数据库中不是null
奇怪的是,列表大小正确,因此它进入了foreach循环。正在正确选择列表,但根据我的调试器,所有属性都为空
对此我感到困惑,于是我跑了这条线:
console.WriteLine(context.Messages.Select(x => x.Recipient.FirstName).FirstOrDefault());
第一封邮件的收件人的名字被写入控制台。因此,当我单独选择时,我可以检索消息的收件人及其所有信息,但当尝试检索整个表并将其存储在列表中时,收件人对象为空
正如我所说,我是从包含上下文的MVC项目之外访问它的。我从另一个项目中使用它。但是,另一个项目包含对我的MVC项目(包含db的消息模型)和另一个项目(包含称为Message的不同类)的引用。这种模棱两可可能是问题的根源,还是我所做的有其他问题
编辑我显然对我的问题产生了一些困惑。问题是,一旦检索到列表,列表的大小就正确了,但是列表中消息对象的参数为空。例如,如果我写:
foreach (Message m in msgs)
{
Console.WriteLine("List Element Exists");
if (m.Recipient != null)
{
Console.WriteLine(m.Recipient.FirstName);
}
}
我得到输出:
列表元素存在
列表元素存在
列表元素存在
列表元素存在
对于列表中的每个元素
JK很可能是linq查询中
条件为null的结果
var info = context.Contacts.Where(x => x.Id == m.recipient.Id)
.Select(x => x.MobileNumber).FirstOrDefault()
此外,查询本身也存在一些问题,您可以编写与以下相同的查询:
var mobileNumber = string.Empty; //if it is not a string then initialize with proper value
var info = context.Contacts.FirstOrDefault(x => x.Id == m.recipient.Id);
if(info != null)
mobileNumber = info.MobileNumber;
还有一个问题,;如果执行此行:
var msgs = context.Messages.ToList();
它将从数据库中获取所有消息
;但是你只需要一个电话号码。因此,与其获取所有记录,不如执行我提供的查询,而不要调用foreach
编辑
执行ToList()
时,立即执行db查询;这意味着将不会加载邮件
对象的收件人
属性。根据您使用的是延迟加载还是快速加载,您需要另一种机制来获取Recipient
属性。有点像
var msgs = context.Messages.Include(b => b.Recipients).ToList();
如果您希望msg.Recipient包含某些内容(即在DB上编译数据),则这是一个映射问题。最常见的问题是收件人属性未标记为虚拟
编辑
或者,甚至最糟糕的是,该类被标记为密封的,但这通常不会发生在控制台上。WriteLine(String)不会在null参数上引发异常。告诉引发异常的确切位置。调试此异常时,null
到底是什么?对于数据库中该字段为null
的任何记录,我预计m.Text
将为null
。如果m为null,则可能是映射问题。此外,文本是否为字符串类型并直接映射到表?文本是否为数据库中的必填字段?我很抱歉,我简化了问题,试图显示孤立的问题。请看编辑。空异常指的是我的邮件的收件人对象。我的邮件有一个必需的收件人,这是一个联系人(我数据库中的另一个实体)。谢谢回复。这仍然抛出异常。异常是因为由于某种原因,收件人
联系人对象在我的邮件列表中为空。我检索所有消息的原因是因为我在Foreach循环中以其他方式使用列表。您看到的这一行是大型流程的第一行。我需要所有的消息…我以前从未遇到过包含函数…但谢谢它工作得很好。所以我想,对于复杂的属性,你必须指定包含它们。我不知道延迟加载和渴望加载,因为我对这个领域很陌生。我只能接受一个答案,但我投了赞成票,因为我从这两个方面都学到了一些东西。谢谢您认为使用“急切加载”只加载给定情况下所需内容的优势更可取吗?