Entity framework 关于如何在实体框架4.1中的多对多关系之间导航的思考

Entity framework 关于如何在实体框架4.1中的多对多关系之间导航的思考,entity-framework,entity-framework-4.1,Entity Framework,Entity Framework 4.1,我不喜欢在模型中多个实体共享的对象上放置导航属性。下面是我所说的一个例子: public abstract class SomeEntity { public Guid Id {get;set; public virtual ICollection<Attachment> Attachements {get;set;} } public class User: SomeEntity {

我不喜欢在模型中多个实体共享的对象上放置导航属性。下面是我所说的一个例子:

    public abstract class SomeEntity
    {
       public Guid Id {get;set;         
       public virtual ICollection<Attachment> Attachements {get;set;}
    }

    public class User: SomeEntity
    {
         ...
    }

    public class Thing: SomeEntity
    {
         ...
    }

    public class Attachment
    {
       public Guid Id {get;set;}         
       ...
    }

查看我的附件表,没有FK返回到任何链接表。这是有道理的,因为我没有导航回它们。

如果您担心延迟加载,那么您可以使导航属性不是虚拟的,这样它就不会启动延迟加载

或者,您可以将导航属性设置为私有,然后以受控方式访问内容。一旦将导航属性设置为私有,您就需要使用其中一个技巧,使用代码优先API映射私有属性。为简单起见,我使用了将EntityConfiguration嵌入实体中的配置:

public class Attachment
{
    public Guid Id { get; set; }

    private ICollection<User> Users { get; set; }

    public class AttachmentConfiguration : EntityTypeConfiguration<Attachment>
    {
        public AttachmentConfiguration()
        {
            HasMany(e => e.Users)
                .WithMany(e => e.Attachements)
                .Map(m =>
                     {
                         m.MapLeftKey("UserId");
                         m.MapRightKey("AttachmentId");
                         m.ToTable("User_Attachments");
                     });
        }
    }
} 
然后,您可以从附件内部以任何方式访问用户,或者从方法等公开用户

您还可以使用DbContext change tracker API从任何有上下文的地方访问它们。例如:

var users = context.Entry(attachment).Collection<User>("Users").CurrentValue;
var users=context.Entry(附件).Collection(“users”).CurrentValue;

如果您真的不想要任何导航属性,那么您可以下拉到ObjectContext并获取集合的RelatedEnd,它将是EntityCollection。这是一个相当棘手的代码,原因有很多,包括需要知道关联的概念模型名称和结束名称,您可以通过转储EDMX找到这些名称。如果可能的话,我会尽量避免这种方法。

如果您担心延迟加载,那么您可以将导航属性设置为非虚拟属性,这样它就不会启动延迟加载

或者,您可以将导航属性设置为私有,然后以受控方式访问内容。一旦将导航属性设置为私有,您就需要使用其中一个技巧,使用代码优先API映射私有属性。为简单起见,我使用了将EntityConfiguration嵌入实体中的配置:

public class Attachment
{
    public Guid Id { get; set; }

    private ICollection<User> Users { get; set; }

    public class AttachmentConfiguration : EntityTypeConfiguration<Attachment>
    {
        public AttachmentConfiguration()
        {
            HasMany(e => e.Users)
                .WithMany(e => e.Attachements)
                .Map(m =>
                     {
                         m.MapLeftKey("UserId");
                         m.MapRightKey("AttachmentId");
                         m.ToTable("User_Attachments");
                     });
        }
    }
} 
然后,您可以从附件内部以任何方式访问用户,或者从方法等公开用户

您还可以使用DbContext change tracker API从任何有上下文的地方访问它们。例如:

var users = context.Entry(attachment).Collection<User>("Users").CurrentValue;
var users=context.Entry(附件).Collection(“users”).CurrentValue;

如果您真的不想要任何导航属性,那么您可以下拉到ObjectContext并获取集合的RelatedEnd,它将是EntityCollection。这是一个相当棘手的代码,原因有很多,包括需要知道关联的概念模型名称和结束名称,您可以通过转储EDMX找到这些名称。如果可能的话,我会尽量避免这种方法。

@LadislavMrnka,如果不在附件实体上使用导航属性,您将如何从附件导航回另一个实体。因此,您是否需要导航属性。如果要向后导航,请创建指向
SomeEntity
集合的导航属性。@LadislavMrnka,我应该更具体地说我正在搜索替代项。我假设人们会阅读字里行间的内容。@LadislavMrnka,如果不在附件实体上使用导航属性,您将如何从附件导航回另一个实体。因此,您是否需要导航属性。如果要向后导航,请创建指向
SomeEntity
集合的导航属性。@LadislavMrnka,我应该更具体地说我正在搜索替代项。我假设人们会在字里行间阅读。映射配置正是我所使用的。这方面的想法很好!我主要担心的是延迟加载,忽略了virtual关键字。习惯于使用它而忘记它的使用;)映射配置正是我正在使用的。这方面的想法很好!我主要担心的是延迟加载,忽略了virtual关键字。习惯于使用它而忘记它的使用;)