C# 实体框架-虚拟属性为空
我有以下的类定义C# 实体框架-虚拟属性为空,c#,entity-framework,C#,Entity Framework,我有以下的类定义 public abstract class AbstractClass { [Key] public string Name { get; set; } public virtual IndependentClass IndependentClass { get; set; } public string IndependentClassName { get { return IndependentClass == null ? "<N
public abstract class AbstractClass
{
[Key]
public string Name { get; set; }
public virtual IndependentClass IndependentClass { get; set; }
public string IndependentClassName { get { return IndependentClass == null ? "<NULL>" : IndependentClass.Name; } }
}
public class Impl1 : AbstractClass
{
}
public class Impl2 : AbstractClass
{
}
public class IndependentClass
{
[Key]
public string Name { get; set; }
public virtual Impl1 Impl1 { get; set; }
public virtual ICollection<Impl2> Impl2s { get; set; }
}
我的初始化如下所示(将数组添加到上下文和context.SaveChanges()
trimmed)
最后,我有一个简单的视图转储每个db集合。我的问题是导航属性没有像我需要的那样被填充。i、 例如,我的观点的输出是:
Independent Classes:
A: Impl1 = a, Impl2s = []
B: Impl1 = b, Impl2s = []
Impl1s
a: IndependentClass = <NULL>
b: IndependentClass = <NULL>
c: IndependentClass = <NULL>
Impl2s
a1: IndependentClass = A
a2: IndependentClass = A
b1: IndependentClass = B
b2: IndependentClass = B
c1: IndependentClass = <NULL>
独立类:
A:Impl1=A,Impl2s=[]
B:Impl1=B,Impl2s=[]
IMP1S
a:独立类=
b:独立类=
c:独立类=
Impl2s
a1:独立类=A
a2:独立类=A
b1:独立类=B
b2:独立类=B
c1:独立类=
IndependentClass应填充其IMPL2,前两个IMPL1应填充IndependentClass
谁能告诉我我做错了什么吗?您需要初始化构造函数中的属性 只有当实例来自EF DataContext时,EF才会为您这样做
当您编写
newimpl2()
时,根本不涉及EF。显然,解决方案是替换
modelBuilder.Entity<AbstractClass>().HasOptional(abs => abs.IndependentClass);
modelBuilder.Entity<IndependentClass>().HasRequired(ind => ind.Impl1);
modelBuilder.Entity<IndependentClass>().HasMany(ind => ind.Impl2s);
modelBuilder.Entity().HasOptional(abs=>abs.IndependentClass);
modelBuilder.Entity().HasRequired(ind=>ind.Impl1);
modelBuilder.Entity().HasMany(ind=>ind.Impl2s);
与
modelBuilder.Entity()
.has可选(abs=>abs.IndependentClass)
.WithRequired(ind=>ind.Impl1);
但我不确定为什么不必为Impl2更改任何内容。您的模型与以下导航属性有三种关系:
AbstractClass.IndependentClass
IndependentClass.(非活动属性)
IndependentClass.Impl1
Impl1.(非活力属性)
IndependentClass.Impl2s
Impl2.(非活力属性)
IndependentClass.Impl2s
,也没有填充Impl1.IndependentClass
。您填写Impl2.IndependentClass
,但由于此导航属性属于另一个关系,因此它根本不会影响IndependentClass.Impl2s
如果你想要两段感情
IndependentClass.Impl1
(一对一)Impl1.IndependentClass
IndependentClass.Impl2s
(一对多)Impl2.IndependentClass
AbstractClass
是模型中具有自己表的实体,您就无法实现这一点,因为您必须在它们声明的类型的导航属性之间进行映射,和Impl1.IndependentClass
和Impl2.IndependentClass
是继承的属性,但它们未在Impl1
和Impl2
中声明
如果您没有将AbstractClass
作为一个实体,即在映射代码时不使用此抽象类,并且在您的上下文类中没有DbSet
,则上述两种关系是可能的。对于EF,您的模型没有任何继承,而是将Impl1
(和Impl2
)视为一个实体,它只包含自己的属性和基类的属性,就好像它是一个没有基类的类一样
这就是为什么您自己的答案中的映射会像您预期的那样工作:您已经使用Fluent API明确定义了
IndependentClass.Impl1
和Impl1.IndependentClass
之间的一对一关系。IndependentClass.Impl2s
和Impl2.IndependentClass
之间的第二个关系是通过将约定命名为一对多关系自动检测的。我的视图从数据上下文获取对象,因此这不是问题所在,因为此映射AbstractClass
不再是实体(并且没有自己的表)与您问题中的映射相反。Impl1.IndependentClass
和Impl2.IndependentClass
现在是两个独立的导航属性(上面的abs
是Impl1
,而不是AbstractClass
),一个是指上面的映射代码定义的IndependentClass.Impl1
,另一个是指按照约定自动映射为一对多的IndependentClass.Impl2s
。您的新模型有两个关系,旧模型有三个。Ohhhh,这很有意义。如果您用这个来回答问题,我会答对了。谢谢!我实际上已经开始写答案了,但当你自己的答案出现时,我就停了下来。幸运的是,我保存了一份草稿,所以我现在可以恢复并扩展一下。
Independent Classes:
A: Impl1 = a, Impl2s = []
B: Impl1 = b, Impl2s = []
Impl1s
a: IndependentClass = <NULL>
b: IndependentClass = <NULL>
c: IndependentClass = <NULL>
Impl2s
a1: IndependentClass = A
a2: IndependentClass = A
b1: IndependentClass = B
b2: IndependentClass = B
c1: IndependentClass = <NULL>
modelBuilder.Entity<AbstractClass>().HasOptional(abs => abs.IndependentClass);
modelBuilder.Entity<IndependentClass>().HasRequired(ind => ind.Impl1);
modelBuilder.Entity<IndependentClass>().HasMany(ind => ind.Impl2s);
modelBuilder.Entity<Impl1>()
.HasOptional(abs => abs.IndependentClass)
.WithRequired(ind => ind.Impl1);