C# 为什么懒散不起作用?
请参阅下面的代码:C# 为什么懒散不起作用?,c#,entity-framework,lazy-loading,proxy-classes,C#,Entity Framework,Lazy Loading,Proxy Classes,请参阅下面的代码: class Program { public class Request { public virtual int RequestId { get; set; } public virtual int LastStatus { get; set; } public virtual RequestType RequestType { get; set; } [InverseProperty("Re
class Program
{
public class Request
{
public virtual int RequestId { get; set; }
public virtual int LastStatus { get; set; }
public virtual RequestType RequestType { get; set; }
[InverseProperty("Request")]
public virtual MembershipRequest MembershipRequest { get; set; }
[InverseProperty("Request")]
public virtual CodingRequest CodingRequest { get; set; }
}
public class MembershipRequest
{
[Key, ForeignKey("Request")]
public virtual int RequestId { get; set; }
public virtual Request Request { get; set; }
public virtual string CompanyName { get; set; }
}
public class CodingRequest
{
[Key, ForeignKey("Request")]
public virtual int RequestId { get; set; }
public virtual Request Request { get; set; }
public virtual string ProductName { get; set; }
}
public enum RequestType
{
MembershipRequest,
CodingRequest
}
public class Context: DbContext
{
public Context()
: base("ConnectionString")
{
}
public DbSet<Request> Requests { get; set; }
public DbSet<MembershipRequest> MembershipRequests { get; set; }
public DbSet<CodingRequest> CodingRequests { get; set; }
}
static void Main(string[] args)
{
Insert();
Select();
}
private static void Select()
{
using (var context = new Context())
{
foreach (var request in context.Requests.ToList())
{
Console.WriteLine(request.RequestType == RequestType.CodingRequest
? request.CodingRequest.ProductName : request.MembershipRequest.CompanyName);
//null reference here^
}
Console.ReadLine();
}
}
private static void Insert()
{
using (var context = new Context())
{
var r1 = new Request
{
LastStatus = 1,
RequestType = RequestType.MembershipRequest,
MembershipRequest = new MembershipRequest
{
CompanyName = "company1"
}
};
context.Requests.Add(r1);
var r2 = new Request
{
LastStatus = 2,
RequestType = RequestType.CodingRequest,
CodingRequest = new CodingRequest
{
ProductName = "Product2"
}
};
context.Requests.Add(r2);
context.SaveChanges();
}
}
}
类程序
{
公共类请求
{
公共虚拟int请求ID{get;set;}
公共虚拟int LastStatus{get;set;}
公共虚拟请求类型请求类型{get;set;}
[反向属性(“请求”)]
公共虚拟成员身份请求成员身份请求{get;set;}
[反向属性(“请求”)]
公共虚拟编码请求编码请求{get;set;}
}
公共类成员资格请求
{
[钥匙,外国钥匙(“请求”)]
公共虚拟int请求ID{get;set;}
公共虚拟请求{get;set;}
公共虚拟字符串CompanyName{get;set;}
}
公共类编码请求
{
[钥匙,外国钥匙(“请求”)]
公共虚拟int请求ID{get;set;}
公共虚拟请求{get;set;}
公共虚拟字符串ProductName{get;set;}
}
公共枚举请求类型
{
会员资格申请,
编码请求
}
公共类上下文:DbContext
{
公共上下文()
:base(“连接字符串”)
{
}
公共数据库集请求{get;set;}
公共数据库集成员身份请求{get;set;}
公共数据库集编码请求{get;set;}
}
静态void Main(字符串[]参数)
{
插入();
选择();
}
私有静态void Select()
{
使用(var context=new context())
{
foreach(context.Requests.ToList()中的var请求)
{
Console.WriteLine(request.RequestType==RequestType.CodingRequest
?request.CodingRequest.ProductName:request.MembershipRequest.CompanyName);
//此处为空引用^
}
Console.ReadLine();
}
}
私有静态void Insert()
{
使用(var context=new context())
{
var r1=新请求
{
LastStatus=1,
RequestType=RequestType.MembershipRequest,
MembershipRequest=新的MembershipRequest
{
CompanyName=“company1”
}
};
context.Requests.Add(r1);
var r2=新请求
{
LastStatus=2,
RequestType=RequestType.CodingRequest,
编码请求=新编码请求
{
ProductName=“产品2”
}
};
context.Requests.Add(r2);
SaveChanges();
}
}
}
在foreach语句中,请求对象的类型为request,而不是动态代理。因此,延迟加载失败了。这些类显然满足了动态代理创建和延迟加载的所有要求
为什么不工作?因为您的实体类嵌套在非公共类
程序中,因此EF无法为它们生成代理类。考虑将您的<代码>程序< /代码>的访问修饰符更改为<代码>公共< /代码>,或者定义您的实体类在<代码>程序> <代码>。< /p>您看到插入在数据库中的数据吗?可能是因为您的实体被定义在另一个类(<代码>程序< /代码>)中,未被标记为“代码>公共< /代码> >(因此默认情况下内部)。我想他们还不具备创建代理的资格。@haim770哇,这确实是原因。观察得很好。你能把这个作为一个答案吗?@Alireza,谢谢。但是现有的答案已经反映了这个发现,那么我想你可以接受。嗯,是的……它已经被编辑过了。上次我读它时,它是关于ToList()
方法。这不是真的。即使迭代的数据是List
,列表中的每个项目都可以是代理类型。默认情况下(当类型可以代理且代理创建未禁用时),这将是一个代理列表。@haim770您肯定是对的。所以我编辑了我的帖子,以更好地回答这个问题。谢谢。