Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/linq/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 从列表中删除重复项<;T>;基于Lambda选择的属性_C#_.net_Linq_List - Fatal编程技术网

C# 从列表中删除重复项<;T>;基于Lambda选择的属性

C# 从列表中删除重复项<;T>;基于Lambda选择的属性,c#,.net,linq,list,C#,.net,Linq,List,我有一个列表,它有几个键。我有几种情况。在某些情况下,我希望基于键1删除重复项,而在其他情况下,我希望基于键2删除重复项。用户对象上的两个属性 我认为这很简单,可以为Distinct函数提供一个通用的IEqualityComparer,如下所示: public class AwesomeEqualityComparerOfDoom<T> : IEqualityComparer<T> where T : class { private readonly Func&l

我有一个
列表
,它有几个键。我有几种情况。在某些情况下,我希望基于键1删除重复项,而在其他情况下,我希望基于键2删除重复项。用户对象上的两个属性

我认为这很简单,可以为Distinct函数提供一个通用的IEqualityComparer,如下所示:

public class AwesomeEqualityComparerOfDoom<T> : IEqualityComparer<T> where T : class
{
    private readonly Func<T, object> compiledFunction;

    public AwesomeEqualityComparerOfDoom(Func<T, object > propertyFunction)
    {
        compiledFunction = propertyFunction;
    }

    public bool Equals(T x, T y)
    {
        object key1 = compiledFunction(x);
        object key2 = compiledFunction(y);
        return key1.Equals(key2);
    }

    public int GetHashCode(T obj)
    {
        return obj.GetHashCode();
    }
}
var comparer = ProjectionEqualityComparer<User>.Create(x => x.Name);
公共类AwesomeEqualityComparerOfDoom:IEqualityComparer其中T:class
{
私有只读Func编译函数;
公共AwesomeEqualityComparerOfDoom(函数属性函数)
{
compiledFunction=propertyFunction;
}
公共布尔等于(TX,TY)
{
对象键1=编译函数(x);
对象键2=编译函数(y);
返回键1.Equals(键2);
}
公共int GetHashCode(T obj)
{
返回obj.GetHashCode();
}
}
当我手动测试这个类时,通过创建它的一个实例,并给它两个具有相同密钥的用户,它就工作了。但是,当我将其传递给Distinct函数时,不会删除重复的用户


我还尝试将IEquality类定义为
AwesomeEqualityComparerOfDoom
,这样它就知道它将调用哪种类型的值,但是没有用。

GetHashCode
实现中没有使用
compiledFunction
,只是使用了项本身的哈希代码。你想要的是:

public int GetHashCode(T obj)
{
    return compiledFunction(obj).GetHashCode();
}
然而:

    你应该考虑把你的类在投影类型中也用,比如(代码)<代码> FUNC<代码>,而不是只是代码> FUNC
  • 应考虑使用<代码>均衡器>代码>处理空键。
我已经在with helper方法中提供了一些类来帮助实现这一点,因此您可以执行以下操作:

public class AwesomeEqualityComparerOfDoom<T> : IEqualityComparer<T> where T : class
{
    private readonly Func<T, object> compiledFunction;

    public AwesomeEqualityComparerOfDoom(Func<T, object > propertyFunction)
    {
        compiledFunction = propertyFunction;
    }

    public bool Equals(T x, T y)
    {
        object key1 = compiledFunction(x);
        object key2 = compiledFunction(y);
        return key1.Equals(key2);
    }

    public int GetHashCode(T obj)
    {
        return obj.GetHashCode();
    }
}
var comparer = ProjectionEqualityComparer<User>.Create(x => x.Name);
var comparer=projectionqualitycomparer.Create(x=>x.Name);
然后从lambda表达式推断密钥类型。

Distinct()
是一个LINQ方法,它返回一个新的序列,但不包含任何重复项。

它不会修改原始列表。

如果
key1
null
,会发生什么情况?调用
Equals(键1,键2)
请添加使用
.Distinct
的代码。