【问题标题】:Using linq and lambda to filter two collections使用 linq 和 lambda 过滤两个集合
【发布时间】:2012-10-04 08:17:41
【问题描述】:

我需要按两个集合过滤查询。

我有一个 ID 列表,我需要用它来过滤 linq 查询

集合看起来像这样

<table1_id, table2_id>

并且内容看起来像这样

idList = <1,10>,<2,12>

查询如下所示

Dim l = (From t1 In Table1
Join t2 In Table2 ON t1.table1_id Equals t2.table2_id
Where idList.Contains(idList.table1_id) and idlist.Contains(idList.table2_id))

问题是这就像一个交叉连接,所以我得到了所有的组合。

怎样才能让两个集合过滤像这样查询

Select * from
table1 t1 Inner join table2 t2 on t1.ID = t2.ID
where t1.ID in (1,2)
and t2.ID in (10, 12)

这是我的代码中的真实示例:

SQL 查询:

    Select * from
dbo.v_MARKET_BUSINESS_ROLES mbs
Inner join dbo.SAP_COMPONENT brs
 on mbs.BUSINESS_ROLE_ID = brs.BUSINESS_ROLE_ID
and mbs.erd in ('1','2')
and brs.ID in (10,12)
where 
brs.market_id = 1

代码:

选择角色有 2 个 id 的 1 和 2,所以我只从列表中收集选定的角色

Dim businessRolesIDs = (From olc In ctx.organization_level_constraint
                                          Where selectedOrgLevels.Contains(olc.organization_level_id) _
                                                            AndAlso olc.market_id = marketId _
                                          AndAlso selectedRoles.Contains(olc.business_role_id)
                                          Select olc.business_role_id, olc.sap_component_id).Distinct.ToList


here I try to filter by the collection returned above

Dim marketBusinessRolesCollection = (From m In ctx.GetMarketBusinessRolesFromView(marketId) _
                                                    Join bs In ctx.business_role_sap_component On m.C_BUSINESS_ROLE_ID Equals bs.business_role_id _
                                                    Where (From item In businessRolesIDs Select item.business_role_id).Contains(m.C_BUSINESS_ROLE_ID)  _
                                                    And (From item2 In businessRolesIDs Select item2.sap_component_id).Contains(bs.sap_component_id)  _
                                                    And bs.market_id = marketId _
                                                    Select New BusinessRole With _
                                                      { 
                                                         .BusinessRoleId = m.ERD
                                                      }).Distinct.ToList

【问题讨论】:

  • 在没有伪代码的情况下查看类和一些数据会非常有帮助。顺便说一句,这是 LINQ to Objects 吗?
  • 您确定 SQL 查询吗? t1.IDt2.ID 是相等的,并且这两个集合没有共同的元素,因此您的 SQL 查询将永远不会显示结果。如果正确,则足以测试 t1.ID 是否在两个集合的交集中。
  • 解释我得到的结果和我期望的是当我运行 sql 查询时我得到 2 个结果,因为连接正确过滤了关系。当我运行 linq 代码时,我得到 4 个结果,因为它的工作方式类似于交叉连接(如果我没记错的话)。实际上,根据查询,我应该只得到 2 个结果。如果我运行 sql 语句,我会从我的数据库中得到两个结果。我会更新帖子并添加一些真实数据...
  • 嗨 Gert,抱歉,我在编写伪代码时可能遗漏了一件小事。在 where 语句中,他们应该共享一个关系,例如 t1.Market_id = 1 和 t2.Market_ID = 1

标签: linq join filter lambda


【解决方案1】:

您必须选择 ID-List 的键和值。 我知道这个集合的构建就像List&lt;KeyValuePair&lt;int, int&gt;&gt;

所以你的代码应该是这样的

Dim l =
    From t1 In Table1
    Join t2 In Table2 ON t1.table1_id Equals t2.table2_id
    Where (From item In idList Select item.Key).Contains(t1.table1_id)
    And (From item In idList Select item.Value).Contains(t2.table2_id);

【讨论】:

  • 这给了我与我上面的代码相同的结果。我没有得到两个结果,而是得到了 4 个结果,因为这两个列表之间没有连接。阅读我上面的评论以及共享关系,其中两者共享相同的market_id。它在 linq 查询中是相同的,但我一直得到 4 个结果,但是当我运行 sql 时,我得到 2 个结果
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2022-11-26
  • 2011-04-21
  • 2012-04-08
  • 1970-01-01
  • 1970-01-01
  • 2012-03-22
  • 1970-01-01
相关资源
最近更新 更多