从另一个列表获取列表的Linq

9

我有两个集合:一个是Items,另一个是ActiveItems

这两个集合之间唯一的交集就是名称

我想用Linq从Items中获取一个列表,其中Items的名称在ActiveItems中具有相同的名称

我编写了以下代码,但是否有更好的方法:

Items.Where(i => ActiveItems.Count(v=> v.Name==i.Name) > 0)
4个回答

16

我会创建一个由ActiveItems中名称组成的集合,然后使用它:

var activeNames = new HashSet<string>(activeItems.Select(x => x.Name));
var itemsWithActiveNames = items.Where(x => activeNames.Contains(x.Name))
                                .ToList();

另一个选项是使用联结,例如使用查询表达式:

var query = from activeItem in activeItems
            join item in items on activeItem.Name equals item.Name
            select item;

请注意,如果有多个名称相同的 ActiveItem 值,则会出现重复的 item 值。另一个备选的连接方法不会出现这个问题,但是有点笨拙:

var query = from item in items
            join activeItem in activeItems 
                on item.Name equals activeItem.Name
                into g
            where g.Any()
            select item;
请注意,所有这些方法都将避免进行O(N * M)的名称检查 - 它们都将在后台使用哈希表,以提供O(N + M)的复杂度。

不,我不想从另一个集合中获取属性。 - Navid Rahmani
方案2和3是否会在activeNames不是其中之一的情况下内部使用HashSets? - Magnus
@Magnus:是的...我只是觉得如果你不需要连接,第一个版本更清晰 :) - Jon Skeet

7
Items.where(i => ActiveItems.Any(a => i.Name == a.Name))

0
var results = from i1 in collection1.Items
              join i2 in collection2.ActiveItems on i1.Name equals i2.Name
              select i2.Name;

0

使用 join:

from item in Items
join active in ActiveItems on item.Name equals active.Name
select item

连接应该是在项目名称等于活动名称的情况下进行。顺序很重要。 - slfan

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接