[英]Entity Framework and (1 to many)-(many to 1) (1 - * * - 1) relations
[英]Entity Framework avoid duplications in many to many relations
我对 EF 6 数据库优先的方法有些困惑。
我在 SQL 服务器中有 3 个表:
我想将数据插入到这种关系中。
从代码中,我得到了我迭代的团队列表
插入:
foreach (var team in teams.Teams)
{
var teamEntity = new Contexts.Team
{
TeamName = team.Name,
....
};
foreach (var member in team.Members)
{
teamEntity.Members.Add(
new Contexts.Member()
{
MemberName = member.Name,
EmailAddress = member.Email,
...
});
}
DbUtility.Context.Teams.Add(teamEntity);
}
我的问题是我在 members 表中发现了很多重复,这不太好。
如何管理插入以避免重复并将 ID 重定向到正确的位置?
在处理关联时,您将希望对相关实体使用相同的引用,而不是为每个相关实体新建一个引用。
如果我要插入多个包含成员的团队,其中一些成员可能是新成员并在团队之间共享,而其他成员可能是数据库中已有的成员:
从那里我们可以开始看下面的东西:
var memberIds = teams.Teams
.SelectMany(t => t.Members)
.Select(m => m.MemberId)
.Where(m => m.MemberId != 0)
.ToList();
var existingMembers = Context.Members
.Where(m => memberIds.Contains(m.MemberId))
.ToList();
foreach (var team in teams.Teams)
{
var teamEntity = new Contexts.Team
{
TeamName = team.Name,
....
};
foreach (var member in team.Members)
{ //We assume that all e-mail addresses are unique.
var existingMember = existingMembers.SingleOrDefault(m => m.Email == member.Email);
if (existingMember == null)
{
existingMember = new Member()
{
MemberName = member.Name,
EmailAddress = member.Email,
...
});
existingMembers.Add(existingMember); // For future reference.
}
teamEntity.Members.Add(existingMember);
}
DbUtility.Context.Teams.Add(teamEntity);
}
第一步是为团队寻找任何现有成员。 如果您知道将不存在现有成员,那么您可以跳过该加载,而只需使用最初为空的集合。 当我们通过我们的团队 go 时,我们首先检查现有集合中是否有与电子邮件地址匹配的成员。 如果我们找到一个,我们使用它,否则我们创建一个新成员并将其添加到集合中。 这样,当添加具有相同成员的另一个团队时,它会在集合中找到并且将使用相同的引用。
当 EF 插入数据时,它尊重引用,不一定是 ID/约束将实体关联到相同的引用,而不是创建重复项。 如果您有 2 个实体引用同一个成员 (joe.smith@gmail.com),那么您要确保两个实体引用 joe.smith 的同一个成员实体,而不是 2 个具有相同电子邮件地址的不同实体。 在处理批量操作(插入许多团队)时,您将希望保留本地缓存或从 DbContext 读取以利用其缓存。 对于单个操作,您应该始终 go 到 DbContext 以在尝试创建新引用之前检索现有实体(如果可用)。 (避免重复数据或违反约束/重复键异常。)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.