在C#中的2个集合之间相交

时间:2016-01-27 09:17:19

标签: c# list collections intersect

我有:

myFunc.prototype.newProperty = "New";

我需要将它与比较id相交。这样的事情:

            List<INFRAESTRUCTURA> l1 = listQ1.ToList();
            List<INFRAESTRUCTURA> l2 = listQ2.ToList();

但我不知道我必须使用哪种方法而且它是sintax。

我发现了这个:

 l1.Intersect(l2, l1[].id_infraestructura == l2[].id_infraestructura) 

但是这会返回一个id列表,我需要两个列表中包含的元素列表。

谢谢!

3 个答案:

答案 0 :(得分:2)

我会使用Enumerable.Join

var intersecting = from i1 in l1
                   join i2 in l2
                   on i1.id_infraestructura equals i2.id_infraestructura
                   select i1;
List<INFRAESTRUCTURA> result = intersecting.ToList();

如果您要覆盖Equals中的GetHashCode + INFRAESTRUCTURA或提供自定义IEqualityComparer<INFRAESTRUCTURA>,您可以直接使用Enumerable.Intersect

List<INFRAESTRUCTURA> result = l1.Intersect(l2).ToList();

这是一个可能的实现:

public class InfrastructureComparer : IEqualityComparer<INFRAESTRUCTURA>
{
    public bool Equals(INFRAESTRUCTURA x, INFRAESTRUCTURA y)
    {
        if (x == null && y == null) return true;
        if (x == null || y == null) return false;
        return x.id_infraestructura == y.id_infraestructura;
    }

    public int GetHashCode(INFRAESTRUCTURA obj)
    {
        if (obj == null) return 0;
        return obj.id_infraestructura;
    }
}

您可以使用像IEqualityComparer<T>这样的重载:

List<INFRAESTRUCTURA> result = l1.Intersect(l2, new InfrastructureComparer()).ToList();

如果你想在结果中同时使用两个对象,你可以使用匿名类型:

var intersecting = from i1 in l1
                   join i2 in l2
                   on i1.id_infraestructura equals i2.id_infraestructura
                   select new { i1, i2 };

答案 1 :(得分:1)

您可以使用Linq Join

l1.Join(l2, l => l.id_infraestructura, r => r.id_infraestructura, (l,r) => l.id_infraestructura);

答案 2 :(得分:0)

其他答案是正确的,但您可以将Intersect与自定义比较器一起使用。您可以通过实现IEqualityComparer<>接口来创建自定义比较器。为了实现这个接口,我们必须实现两个方法EqualsGetHashCode

public class InfraestructuraComparer: IEqualityComparer<INFRAESTRUCTURA>
{
    /// <summary>
    /// Whether the two INFRAESTRUCTURA are equal.
    /// </summary>
    public bool Equals(INFRAESTRUCTURA firstObj, INFRAESTRUCTURA secondObj)
    {
        if (firstObj == null && secondObj == null)
            return true;

        if (firstObj == null || secondObj == null)
            return false;

        // Your equality logic goes to here
        return firstObj.ID == secondObj.ID;
    }

    /// <summary>
    /// Return the hash code for this instance.
    /// </summary>
    public int GetHashCode(INFRAESTRUCTURA obj)
    {
        // Don't compute hash code on null object.
        if (obj == null) return 0;

        unchecked
        {
            var hash = 17;

            hash = hash * 23 + obj.Id.GetHashCode();

            return hash;    
        }
    }
}

然后:

var result = list1.Intersect(list2, new InfraestructuraComparer());

您也可以在Except方法中使用此比较器来查找两个序列的差异。

var result = list1.Except(list2, new InfraestructuraComparer());

<强> 此外:

从第一个角度来看,您可能会误解GetHashCode()。您可以在StackOverflow的许多问题中阅读有关此方法的信息。您可以阅读此问题的answer