.net 如何首先使用实体框架代码确定多对多连接表名称?
我知道代码首先使用约定进行模型绑定,这是默认情况下可用(和活动?)的约定 对于多对多关系,连接表名称的选择似乎有点随机.net 如何首先使用实体框架代码确定多对多连接表名称?,.net,entity-framework-4.1,code-first,.net,Entity Framework 4.1,Code First,我知道代码首先使用约定进行模型绑定,这是默认情况下可用(和活动?)的约定 对于多对多关系,连接表名称的选择似乎有点随机 哪些引用的约定用于确定连接表名称?用于确定该名称的算法是什么?我认为,多对多联接表名称的一般规则是 自由的类别名称+紧缩的多重类别名称 因此,如果第一个实体是User,第二个实体是Role,则联接表名称是UserRoles 删除PluralizingTableNameConvention可能会影响这一点,但我不确定 更大的问题是确定什么是“左”和什么是“右”实体。我认为这取决于
哪些引用的约定用于确定连接表名称?用于确定该名称的算法是什么?我认为,多对多联接表名称的一般规则是 自由的类别名称+紧缩的多重类别名称 因此,如果第一个实体是
User
,第二个实体是Role
,则联接表名称是UserRoles
删除PluralizingTableNameConvention
可能会影响这一点,但我不确定
更大的问题是确定什么是“左”和什么是“右”实体。我认为这取决于几乎随机的因素,比如EF构建模型的顺序,反过来又取决于实体之间的导航属性,以及在派生上下文中编写DbSet
s的顺序。因此,强烈建议使用Fluent API明确定义联接表名称。在您的模型中进行一点小小的更改或更改上下文中集合的顺序可能会让您认为名称必须是RoleUsers
,而不是以前的UserRoles
这是一本书
编辑
使用Fluent API明确定义多对多映射的另一个原因是性能(与表名问题没有太大关系,更多的是关于什么应该是左实体,什么应该是右实体)
联接表有一个复合主键和该键上的聚集索引(至少在SQL Server中是这样)。现在假设表名为RoleUsers
,左侧实体为Role
,右侧实体为User
,因为可能有开发人员决定在上下文中按字母顺序对集合进行排序:
public DbSet<Role> Roles { get; set; }
public DbSet<User> Users { get; set; }
现在,应用程序中的大多数查询可能都对获取给定用户的角色感兴趣。但是,您并不经常或从未对获取给定角色的所有用户感兴趣。给定用户的角色可以通过Include
查询:
var user = context.Users.Include(u => u.Roles).Single(u => u.UserId == 1);
这将在联接表中的UserId
上创建SQL联接:on Users.UserId=RoleUsers.UserId
。此联接不能使用联接表中的索引,而是导致表扫描以检索表中用于用户角色ID的第1、3和5行
这样的查询性能更好的方法是将用户
作为左侧实体,将角色
作为右侧实体,从而生成对的聚集索引(UserId,RoleId),这样的查询性能更好。(当然,您可以在上面的示例中创建第二个索引来提高性能。)要实现这一点,必须使用Fluent API指定映射
因此,明智地选择左右实体是有意义的,不要把这个决定留给EF
var user = context.Users.Include(u => u.Roles).Single(u => u.UserId == 1);