【问题标题】:Filtering on Many to Many relationship过滤多对多关系
【发布时间】:2017-12-01 00:03:55
【问题描述】:

我有 3 个具有一对多关系的相关实体。 帐号 1-* 收藏 1-* 物品

每个都与用户有多对多的关系,(与连接表 AccountManagers 、 CollectionManagers 、 ItemManagers )

如果用户在任何连接表中,我正在尝试获取用户的集合列表。 我在想创建 3 个表达式,然后在最后合并 3 个结果并以某种方式删除重复项。 似乎 Lambda 表达式是要走的路,但我仍在学习它们。

我认为中间的更容易,比如 db.Collections.where(C => C.CollectionManagers.UserID == CurrentUserID)

但是您将如何从用户帐户管理器和项目管理器条目中收集集合列表?

提前致谢

【问题讨论】:

  • 我假设 CollectionManagers 是一个多对多的列表,所以你需要更像 Collections.Where(c => c.CollectionManagers.Any(a => a.UserID == CurrentUserID)) 的东西。
  • 如果您发布您正在谈论的实体类的相关部分(尤其是导航属性),它会更容易帮助您。

标签: entity-framework asp.net-web-api lambda linq-to-sql


【解决方案1】:

使用 LINQ,Union 运算符将仅返回唯一的 Collection 行,因此组装每个类别并将它们组合起来应该可以工作。

对于Items,我认为找到当前用户管理的所有Items,然后找到它们所属的所有集合是最有效的:

var iCollections = Items.Where(i => i.ItemManagers.Any(im => im.UserId == CurrentUserID)).SelectMany(i => Collections.Where(c => c.Items.Contains(i)));

也可以通过其他方式执行此操作,例如查找包含当前用户管理的 Item 的所有 Collections:

var iCollections = Collections.Where(c => c.Items.Any(i => i.ItemManagers.Any(im => im.UserId == CurrentUserID)));

对于集合,正如您所指出的,您只需要找到当前用户管理集合的所有集合:

var cCollections = Collections.Where(c => c.CollectionManagers.Any(cm => cm.UserId == CurrentUserID));

对于帐户,我们会查找当前用户管理的所有帐户,然后是该帐户拥有的所有集合:

var aCollections = Accounts.Where(a => a.AccountManagers.Any(am => am.UserId == CurrentUserID)).SelectMany(a => a.Collections);

那你可以Union一起查询结果:

var CurrentUserCollections = iCollections.Union(cCollections).Union(aCollections);

【讨论】:

  • 谢谢。我没有意识到您可以将“i”进一步放在其他语句中。 )).SelectMany(i => Collections.Where(c => c.Items.Contains(i)));
  • 请记住,lambda 只是委托的简写,它只是函数的简写,它可以像块一样访问父范围。
猜你喜欢
  • 2020-06-18
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-05-20
  • 2017-04-26
相关资源
最近更新 更多