.net 实体框架:有效地检索数据(多对多关系)

.net 实体框架:有效地检索数据(多对多关系),.net,entity-framework,relational-database,.net,Entity Framework,Relational Database,我正在使用实体框架构建一个简单的身份验证模型。 我创建了四个表:User、Group、Role和GroupUsers 结构如下所示(为了简单起见,我将从表中删除不相关的字段 用户表格 public class User { public int Id {get; set;} public string UserName {get; set;} public string Password {get; set;} public ICollection<Grou

我正在使用实体框架构建一个简单的身份验证模型。 我创建了四个表:
User
Group
Role
GroupUsers

结构如下所示(为了简单起见,我将从表中删除不相关的字段

用户表格

public class User
{
    public int Id {get; set;}
    public string UserName {get; set;}
    public string Password {get; set;}
    public ICollection<Group> Groups { get; set; }
}
public class Group
{
    public int Id {get; set;}
    public string Name {get; set;}
    public ICollection<User> Users{ get; set; }   <- many to amny relationship
    public ICollection<Role> Roles { get; set; }  <- aone to Many relationship
}
public class Role
{
    public int Id {get; set;}
    public string Name {get; set;}
    public Group Group {get; set;}
    public int GroupId {get; set;}
}
GroupUsers表(用于保存多对多关系)

然而,当我运行代码并检查SQL探查器时,它产生了一个非常复杂的SQL!而我希望看到一个简单的左连接脚本

exec sp_executesql N'SELECT 
[Project2].[Id] AS [Id], 
[Project2].[UserName] AS [UserName], 
[Project2].[Password] AS [Password], 
[Project2].[Name] AS [Name], 
[Project2].[Gender] AS [Gender], 
[Project2].[Email] AS [Email], 
[Project2].[EmailConfirmed] AS [EmailConfirmed], 
[Project2].[Mobile] AS [Mobile], 
[Project2].[MobileConfirmed] AS [MobileConfirmed], 
[Project2].[ActiveAccount] AS [ActiveAccount], 
[Project2].[C2] AS [C1], 
[Project2].[GroupId] AS [GroupId], 
[Project2].[UserId] AS [UserId], 
[Project2].[Id1] AS [Id1], 
[Project2].[Name1] AS [Name1], 
[Project2].[Description] AS [Description], 
[Project2].[C1] AS [C2], 
[Project2].[Id2] AS [Id2], 
[Project2].[Name2] AS [Name2], 
[Project2].[Description1] AS [Description1], 
[Project2].[GroupId1] AS [GroupId1]
FROM ( SELECT 
    [Limit1].[Id] AS [Id], 
    [Limit1].[UserName] AS [UserName], 
    [Limit1].[Password] AS [Password], 
    [Limit1].[Name] AS [Name], 
    [Limit1].[Gender] AS [Gender], 
    [Limit1].[Email] AS [Email], 
    [Limit1].[EmailConfirmed] AS [EmailConfirmed], 
    [Limit1].[Mobile] AS [Mobile], 
    [Limit1].[MobileConfirmed] AS [MobileConfirmed], 
    [Limit1].[ActiveAccount] AS [ActiveAccount], 
    [Join2].[GroupId1] AS [GroupId], 
    [Join2].[UserId] AS [UserId], 
    [Join2].[Id1] AS [Id1], 
    [Join2].[Name1] AS [Name1], 
    [Join2].[Description1] AS [Description], 
    [Join2].[Id2] AS [Id2], 
    [Join2].[Name2] AS [Name2], 
    [Join2].[Description2] AS [Description1], 
    [Join2].[GroupId2] AS [GroupId1], 
    CASE WHEN ([Join2].[GroupId1] IS NULL) THEN CAST(NULL AS int) WHEN ([Join2].[Id2] IS NULL) THEN CAST(NULL AS int) ELSE 1 END AS [C1], 
    CASE WHEN ([Join2].[GroupId1] IS NULL) THEN CAST(NULL AS int) ELSE 1 END AS [C2]
    FROM   (SELECT TOP (1) 
        [Extent1].[Id] AS [Id], 
        [Extent1].[UserName] AS [UserName], 
        [Extent1].[Password] AS [Password], 
        [Extent1].[Name] AS [Name], 
        [Extent1].[Gender] AS [Gender], 
        [Extent1].[Email] AS [Email], 
        [Extent1].[EmailConfirmed] AS [EmailConfirmed], 
        [Extent1].[Mobile] AS [Mobile], 
        [Extent1].[MobileConfirmed] AS [MobileConfirmed], 
        [Extent1].[ActiveAccount] AS [ActiveAccount]
        FROM [dbo].[Users] AS [Extent1]
        WHERE [Extent1].[Id] = @p__linq__0 ) AS [Limit1]
    LEFT OUTER JOIN  (SELECT [Extent2].[GroupId] AS [GroupId1], [Extent2].[UserId] AS [UserId], [Extent3].[Id] AS [Id1], [Extent3].[Name] AS [Name1], [Extent3].[Description] AS [Description1], [Extent4].[Id] AS [Id2], [Extent4].[Name] AS [Name2], [Extent4].[Description] AS [Description2], [Extent4].[GroupId] AS [GroupId2]
        FROM   [dbo].[GroupUsers] AS [Extent2]
        INNER JOIN [dbo].[Groups] AS [Extent3] ON [Extent3].[Id] = [Extent2].[GroupId]
        LEFT OUTER JOIN [dbo].[Roles] AS [Extent4] ON [Extent3].[Id] = [Extent4].[GroupId] ) AS [Join2] ON [Limit1].[Id] = [Join2].[UserId]
)  AS [Project2]
ORDER BY [Project2].[Id] ASC, [Project2].[C2] ASC, [Project2].[GroupId] ASC, [Project2].[UserId] ASC, [Project2].[Id1] ASC, [Project2].[C1] ASC',N'@p__linq__0 int',@p__linq__0= 1
我错过什么了吗


有谁能建议一种高效(有利于性能)的方法来获得用户角色吗?

首先,您必须修复GroupUsers

public class GroupUser
{
    public int UserId {get; set;}
      public int GroupId {get; set;}
    public virtual User User { get; set; }
    public virtual Group> Group { get; set; }
}
以及查询

var userRoles=  (from r in  SOContext.Roles
                join gu in SOContext.GroupUsers on r.GroupId equals gu.GroupId
                 where  (gu.UserId == id)
                 select r ).ToList();  

非常感谢,效果非常好!
public class GroupUser
{
    public int UserId {get; set;}
      public int GroupId {get; set;}
    public virtual User User { get; set; }
    public virtual Group> Group { get; set; }
}
var userRoles=  (from r in  SOContext.Roles
                join gu in SOContext.GroupUsers on r.GroupId equals gu.GroupId
                 where  (gu.UserId == id)
                 select r ).ToList();