C# 更改代码以提高性能(快速加载)
我有以下代码用于查找C# 更改代码以提高性能(快速加载),c#,entity-framework,entity-framework-core,C#,Entity Framework,Entity Framework Core,我有以下代码用于查找UserInfo和在UserRole中查找用户角色,以及从role中查找角色信息 我使用的是身份表 这是我的代码: public virtual async Task<ActionResult<List<User>>> GetuserList(CancellationToken cancellationToken) { var userDto = new UserDto(); var users = await userMa
UserInfo
和在UserRole
中查找用户角色,以及从role
中查找角色信息
我使用的是身份表
这是我的代码:
public virtual async Task<ActionResult<List<User>>> GetuserList(CancellationToken cancellationToken)
{
var userDto = new UserDto();
var users = await userManager.Users.Include(x => x.UserRoles).ThenInclude(t=>t.Role).ToListAsync();
return users;
}
但是我仍然需要在
RoleTabel
上找到RoleName
,但是它不能在选择中使用包含。如何使用findRoleName
?我有一些类似的东西,希望能有所帮助。它的性能很好
if (users != null && users.Length > 0 )
{
foreach (var item in users)
{
var userRoles = await UserManager.GetRolesAsync(item);
if (userRoles.Contains("Foreman"))
{
CW.AddRange(db.CrewMemberForeman.Where(x => x.AssignedForemanId == item).Select(x => x.CrewMember).OrderBy(x => x.FirstName).ToList());
}
}
}
我有一些类似的东西,希望能有所帮助。它的性能很好
if (users != null && users.Length > 0 )
{
foreach (var item in users)
{
var userRoles = await UserManager.GetRolesAsync(item);
if (userRoles.Contains("Foreman"))
{
CW.AddRange(db.CrewMemberForeman.Where(x => x.AssignedForemanId == item).Select(x => x.CrewMember).OrderBy(x => x.FirstName).ToList());
}
}
}
在调用对数据源执行查询的ToListAsync()
之前,您可以使用Include
,然后Include
,选择
,Where
等来塑造查询。。特征
你应该做的是把你的第一个任务和你的更新上的投影结合起来
public virtual async Task<ActionResult<List<User>>> GetuserList(CancellationToken cancellationToken)
{
var userDto = new UserDto();
var users = await userManager.Users.Include(x => x.UserRoles).ThenInclude(t=>t.Role)
.Select(x => new UserDto
{
UserName = x.UserName,
Email = x.Email,
Family = x.Family,
Name = x.Name,
Password = x.PasswordHash,
PhoneNumber = x.PhoneNumber,
RoleId = x.UserRoles.FirstOrDefault(t => t.UserId == x.Id).UserId
})
.ToListAsync();
return users;
}
公共虚拟异步任务GetuserList(CancellationToken CancellationToken)
{
var userDto=new userDto();
var users=await userManager.users.Include(x=>x.UserRoles)。然后Include(t=>t.Role)
.选择(x=>newuserdto
{
UserName=x.UserName,
Email=x.电子邮件,
家庭=x.家庭,
Name=x.Name,
Password=x.PasswordHash,
PhoneNumber=x.PhoneNumber,
RoleId=x.UserRoles.FirstOrDefault(t=>t.UserId==x.Id).UserId
})
.ToListAsync();
返回用户;
}
在调用对数据源执行查询的toListSync()
之前,您可以使用包含
,然后包含
,选择
,其中
,等等来塑造查询。。特征
你应该做的是把你的第一个任务和你的更新上的投影结合起来
public virtual async Task<ActionResult<List<User>>> GetuserList(CancellationToken cancellationToken)
{
var userDto = new UserDto();
var users = await userManager.Users.Include(x => x.UserRoles).ThenInclude(t=>t.Role)
.Select(x => new UserDto
{
UserName = x.UserName,
Email = x.Email,
Family = x.Family,
Name = x.Name,
Password = x.PasswordHash,
PhoneNumber = x.PhoneNumber,
RoleId = x.UserRoles.FirstOrDefault(t => t.UserId == x.Id).UserId
})
.ToListAsync();
return users;
}
公共虚拟异步任务GetuserList(CancellationToken CancellationToken)
{
var userDto=new userDto();
var users=await userManager.users.Include(x=>x.UserRoles)。然后Include(t=>t.Role)
.选择(x=>newuserdto
{
UserName=x.UserName,
Email=x.电子邮件,
家庭=x.家庭,
Name=x.Name,
Password=x.PasswordHash,
PhoneNumber=x.PhoneNumber,
RoleId=x.UserRoles.FirstOrDefault(t=>t.UserId==x.Id).UserId
})
.ToListAsync();
返回用户;
}
要从嵌套的子表引用中进行选择,我使用的方法是选择一个匿名类型来构建一个高效的查询,然后进一步将其缩减到DTO中
例如:
var users = userManager.Users.Select(x => new
{
UserName = x.UserName,
Email = x.Email,
Family = x.Family,
Name = x.Name,
Password = x.PasswordHash,
PhoneNumber = x.PhoneNumber,
Role = x.UserRoles.Select(r => new { r.RoleId, r.Role.RoleName}).FirstOrDefault()
}).ToList()
.Select(x => new UserDto
{
UserName = x.UserName,
Email = x.Email,
Family = x.Family,
Name = x.Name,
Password = x.PasswordHash,
PhoneNumber = x.PhoneNumber,
RoleId = x.Role?.RoleId,
RoleName = x.Role?.RoleName
}).ToList();
您可以使用单个。选择,但这可能会导致SQL效率降低,因为每个内部。FirstOrDefault()
等可能会重新加入UserRole/Role表。这样,第一个.Select()
为包含我们所需的子数据的嵌套结构构建SQL,然后第二个跨生成的POCO匿名类型进行操作,以构造要返回的平面DTO
最后一件事,当使用.First()
/.FirstOrDefault()
时,如果您只希望从可能的多个条目中选择一个条目,则应该使用.OrderBy()
子句来确保可预测的结果
此外,鉴于我们使用.Select()
映射输出,您不需要使用.Include()
从相关实体中进行选择。您也不需要User.UserRoles中的.Where()
子句。(User.UserRoles将仅包含该UserId的UserRoles),您将看到。Where()
子句用于从DbContext连接松散关联的表。最好通过映射的FKs建立直接相关的实体关系
编辑:如果每个用户都可能没有角色,则在第二个.Select()
中,您需要使用“?”操作符来检索角色ID和名称。这意味着DTO角色ID必须可以为null。如果您希望将RoleId设置为默认值0或类似值,则可以使用RoleId=x.Role?.RoleId??0
要从嵌套的子表引用中进行选择,我使用的方法是选择一个匿名类型来构建一个高效的查询,然后进一步将其缩减到DTO中
例如:
var users = userManager.Users.Select(x => new
{
UserName = x.UserName,
Email = x.Email,
Family = x.Family,
Name = x.Name,
Password = x.PasswordHash,
PhoneNumber = x.PhoneNumber,
Role = x.UserRoles.Select(r => new { r.RoleId, r.Role.RoleName}).FirstOrDefault()
}).ToList()
.Select(x => new UserDto
{
UserName = x.UserName,
Email = x.Email,
Family = x.Family,
Name = x.Name,
Password = x.PasswordHash,
PhoneNumber = x.PhoneNumber,
RoleId = x.Role?.RoleId,
RoleName = x.Role?.RoleName
}).ToList();
您可以使用单个。选择,但这可能会导致SQL效率降低,因为每个内部。FirstOrDefault()
等可能会重新加入UserRole/Role表。这样,第一个.Select()
为包含我们所需的子数据的嵌套结构构建SQL,然后第二个跨生成的POCO匿名类型进行操作,以构造要返回的平面DTO
最后一件事,当使用.First()
/.FirstOrDefault()
时,如果您只希望从可能的多个条目中选择一个条目,则应该使用.OrderBy()
子句来确保可预测的结果
此外,鉴于我们使用.Select()
映射输出,您不需要使用.Include()
从相关实体中进行选择。您也不需要User.UserRoles中的.Where()
子句。(User.UserRoles将仅包含该UserId的UserRoles),您将看到。Where()
子句用于从DbContext连接松散关联的表。最好通过映射的FKs建立直接相关的实体关系
编辑:如果每个用户都可能没有角色,则在第二个.Select()
中,您需要使用“?”操作符来检索角色ID和名称。这意味着DTO角色ID必须可以为null。如果您希望将RoleId设置为默认值0或类似值,则可以使用RoleId=x.Role?.RoleId??0
您可以将投影与选择一起使用,以获取您的角色ID
。请参阅此问题:@RahulSharma我需要使用UserRole
表查找RoleName
。我如何在投影中使用include?您能指定返回y是多少吗