了解多对多关系和实体框架

时间:2010-06-02 13:46:37

标签: entity-framework linq-to-entities many-to-many

我正在尝试了解实体框架,我有一个表“Users”和一个表“Pages”。这些与关联表“UserPages”的多对多关系相关。首先,我想知道我是否正在使用多对多正确设计这种关系:一个用户可以访问多个页面,每个页面都可以被多个用户访问...,所以我正确使用many2many?

其次,更重要的是,正如我所理解的m2m关系一样,User和Page表不应重复信息。即每个用户和每个页面应该只有一条记录。但是在实体框架中,我如何能够为同一个用户添加同一页面的新访问?也就是说,我以为我可以简单地使用LINQ查询返回的IEnumerable上的Count()方法来获取用户访问某个页面的次数。

但我认为没办法做到这一点。在Linq to Sql中,我可以访问联结表并在那里添加记录,以反映某个用户对某个页面的访问次数,这是必要的次数。但在EF中我无法访问联结表。我只能从User转到Pages集合,反之亦然。

我确定我误解了关系或其他什么,但我无法弄清楚如何对此进行建模。我总是可以在Page表中有一个Count列,但据我所知,你不应该像这样设计数据库表,那些值应该由查询收集......

请帮助我理解我做错了什么......

1 个答案:

答案 0 :(得分:4)

你做对了

在实体数据模型(EDM)多对多关系可以表示有或没有连接表,具体取决于它是否包含一些其他字段。有关详细信息,请参阅以下文章。


在您的情况下,用户实体将直接引用页面实体的集合,反之亦然,因为您的模型不包含的映射User_Page 加入表。

为了添加对用户特定页面的访问,您可以执行以下操作:

using (var context = new YourEntityModelObjectContext())
{
     var page = context.Pages.FirstOrDefault(p => p.Url == "http://someurl");
     var user = context.Users.FirstOrDefault(u => u.Username == "someuser");

     user.Pages.Add(page);

     context.SaveChanges();
}

或者你可以从关系的另一端做到:

using (var context = new YourEntityModelObjectContext())
{
     var page = context.Pages.FirstOrDefault(p => p.Url == "http://someurl");
     var user = context.Users.FirstOrDefault(u => u.Username == "someuser");

     page.Users.Add(user);

     context.SaveChanges();
}

在这两种情况下,新记录都会添加到 User_Page 联接表中。

如果您需要检索特定用户访问的页面数量,您可以执行以下操作:

using (var context = new YourEntityModelObjectContext())
{
     var user = context.Users.FirstOrDefault(u => u.Username == "someuser");
     var visitCount = user.Pages.Count;
}

相关资源: