1

我最近刚刚开始在一个 ASP.NET 项目中使用实体框架(我最近也刚刚开始使用它,所以我最近有点不知所措)

我有一个有 4 个查找表的数据库。当我将 ADO.Net 实体添加到我的 asp.net 项目时,我起初对我的查找表消失的原因感到困惑。在看了一些之后,我偶然发现了这个:

实体框架查找表

并意识到查找没有其他列但外键成为多对多关系的表。这一切都很好。我可能在这里遗漏了一些简单的东西,恐怕可能是这种情况,但现在我迷失了如何查询我最初在遍历查找表时没有问题的数据。

这是我的数据库的通用模型(不是 EDM)

人:PID

组: GID

要求:RID

行动:援助

个人/组:PID GID

组/要求:GID RID

要求/行动:RID AID

人物/动作:PID AID

因此,现在有了 Person、Group、Requirement 和 Action 之间的多对多关系,我不确定如何在我的 ASP.Net Web 表单项目代码中构造语句来遍历这些关系,就像我过去使用查找表一样。

我曾经能够查询 PID = "desired person's id" 的 Person/Group,然后使用 GID 从 Group/Requirement 中查找所有 RID。然后使用 RID 从 Requirement/Action 中查找所有 AID。然后将这些 AID 与 AID 匹配的 Person/Action 中的所有 AID 进行比较,以检查是否满足要求。

如果你告诉我这是我忽略的 ASP.NET 中的基本内容,我不会受到侮辱,但我想如果我在这里问并且得到了回答,那么对于从 SQL 查询切换到实体的任何人来说,至少会有一个简明的答案框架。

4

3 回答 3

1

每当您获得 Person 对象时,您将拥有 Actions 和 Groups 的属性。

组也应该具有 Requirement 属性。

所以我认为你正在寻找的是类似的东西

list<int> personIds = {1,2,3};
List<Requirement> requirements = dbContext.Groups.Where(x => x.Person.Count(y => personIds.Contains(y.PersonId) > 0).Select(x => x.Requirements);
List<Action> actions = requirements.Actions;

你也许可以用一种更巧妙的方式来完成这项工作,当我也在 E​​F 工作时,多对多的关系总是有点痛苦。

于 2013-03-29T20:41:35.513 回答
1

在 EntityFramework 中,您可以选择添加所谓的“导航属性”。例如,让我们看看假设的 Person 类中的这些代码片段。

1 : 1 或 1 : 从 1 的角度来看很多

public class Person
{
  public virtual Group Group {get;set;}
}

Many : Many or 1 : Many 从 Many 的角​​度来看

public class Person
{
  public virtual ICollection<Group> Groups {get;set;}
}

在多对多关系的情况下,您将使用EntityFramework FluentAPI来设置您的 Person 和 Group 类之间的关系。对于 1 对 1 或 1 对多,您可以使用 FluentAPI、DataAnnotations或让 EntityFramework 猜测(我相信它会猜测 PropertyName_ID)。

属性声明中的virtual意味着我允许 EntityFramework在我实际使用它时延迟加载集合,而不是在我查询上下文时。您可以在没有 virtual 关键字的情况下声明导航属性,但不能延迟加载它。

希望这可以帮助您了解导航您的实体。我用粗体表示了一些我认为你应该用谷歌搜索的术语,以帮助进一步了解 EntityFramework 的运作方式。

从您获取给定人员的组所需的所有操作的问题中:

var requiredActions = myPerson.Groups.SelectMany(x => x.Requirements).SelectMany(x => x.Actions);

一个人执行的动作是:

var performedActions = myPerson.Actions;

这两行都假定您已经设置了适当的导航属性。

于 2013-03-29T20:44:53.720 回答
0

如前所述,通过多对多关联,您将在实体中找到集合属性。PersonGroupsGroup将有Persons

如果您进行如下查询

db.Persons.Where(p => p.PID == 1).SelectMany(p => p.Groups)

您将获得所有Person1 组。EF 构建了一个查询,该查询将Person/Group联结表连接了两次。

综合(或“查询”)语法可能更适合您:

from p in db.Persons
from g in p.Groups
where p.PID == 1
select g

现在您的情况可能可以通过这样的查询来解决:

from p in db.Persons
from g in p.Groups
from r in g.Requirements
from ra in r.Actions
from pa in p.Actions
where p.PID == 1
where ra.AID == pa.AID
select new { <properties from entities above> }

但我真的不能从你的问题中看出。不过,这应该可以帮助您了解要点。

于 2013-03-29T21:14:31.053 回答