在linq连接中是否存在“不相等”

问题描述 投票:28回答:4

我正在尝试完成下面的LINQ查询,但我需要一个“不等于”而不是相等,以便filteredEmployees拥有groupA减去groupB的所有员工。

List<Employee> groupA = getEmployeeA();
List<Employee> groupB = getEmployeeB();        

var filteredEmployees = from a in groupA 
                        join b in groupB on a.Name equals b.Name
                        select a;
linq join equals
4个回答
52
投票

您不需要加入:

var filteredEmployees = groupA.Except(groupB);

请注意,这将是一系列独特的员工 - 所以如果groupA中有任何重复项,它们只会在filteredEmployees中出现一次。当然,它也假设你有一个合理的平等比较1。如果你需要特别注明名字,你可以使用ExceptByMoreLINQ

var filteredEmployees = groupA.ExceptBy(groupB, employee => employee.Name);

或者不进入第三方库:

var groupBNames = new HashSet<string>(groupB.Select(x => x.Name));
var filteredEmployees = groupA.Where(x => !groupBNames.Contains(x.Name));

1正如评论中所指出的,你可以将IEqualityComparer<T>作为参数传递给Except。我在ProjectionEqualityComparer有一个MiscUtil类,可以很容易地构建一个你需要的比较器:

// I can't remember the exact method name, but it's like this :)
var comparer = ProjectionEqualityComparer<Employee>.Create(x => x.Name);
var filteredEmployees = groupA.Except(groupB, comparer);

4
投票

不,“不等于”运算符会获得groupA和groupB的所有组合,除了项目相同的组合。

使用Except方法可以获得您想要的内容:

var filteredEmployees = groupA.Except(groupB);

3
投票

在Entity Framework 6中,我使用了更好的结果

var filteredEmployees = groupA.Where(a => !groupB.Select(b => b.Name).Contains(a.Name));

0
投票

使用此代码降低服务器成本:

与其他代码相比,代码的工作速度非常快

        var noExistList = (from n in groupA 
                                join o in groupA  on n.Id equals o.Id into p
                                where p.Count() == 0
                                select n).ToList();

注意:groupA是一个新的添加列表。

© www.soinside.com 2019 - 2024. All rights reserved.