zoukankan      html  css  js  c++  java
  • 小谈IEqualityComparer<T>接口

     今天,想使用自定义的类型作为Dictionary<TKey, TValue> 的键类型,不可避免的要使用到这个接口。如果另外定义一个实现类,使用者必须首先知道有这个类存在,这样调用方才会得到正确的结果。自然想到的办法就是这个自定义类型主动实现IEqualityComparer<T>接口,但是Dictionary<TKey, TValue> 类型并不会去检查这个键对象有没有实现IEqualityComparer<T>接口。

         如果构造Dictionary<TKey, TValue> 泛型集合的实例对象时候,没有提供一个实现了IEqualityComparer<T>接口的实例对象,Dictionary<TKey, TValue>默认使用EqualityComparer<T> 泛型类的 Default属性。看看IEqualityComparer<T>接口MSDN的说明:使用此接口,可以实现集合的自定义相等比较。也就是说,对于类型 T,您可以创建自己的相等定义,并指定该定义可与接受 IEqualityComparer<T>泛型接口的集合类型一起使用。在 .NET Framework 中,Dictionary<TKey, TValue> 泛型集合类型的构造函数接受此接口。继续看EqualityComparer<T> 泛型类Default属性的MSDN的说明:Default 属性检查类型 T 是否实现此 System.IEquatable<T> 泛型接口,如果实现,该属性将返回一个使用该实现的 EqualityComparer<T>。否则,它返回一个使用 T 提供的 Object.Equals 和 Object.GetHashCode 的重写的 EqualityComparer<T>。

         看到上面的说明,我天真的以为实现了System.IEquatable<T> 泛型接口就可以在Dictionary<TKey, TValue> 泛型集合的键中使用自己定义的类了。结果发现无论如何都不能使程序按照设想中的运行。最后发现MSDN中关于System.IEquatable<T>的实现者说明:如果实现 IEquatable<T>,还应重写 Object.Equals(Object) 和 GetHashCode 的基类实现,以便其行为与 IEquatable<T>.Equals 方法的行为一致。尝试着重写了这两个方法,一切都OK了。后来查看了.Net Framework源代码才明白了,实际上,对于EqualityComparer<T> 泛型类来说前面这个重写是必须的,因为前面说的“Default 属性检查类型 T 是否实现此 System.IEquatable<T> 泛型接口,如果实现,该属性将返回一个使用该实现的 EqualityComparer<T>”,实际上这个未公开的 System.IEquatable<T>实现内部其实使用的还是Object.Equals(Object)方法来做比较。

         这就比较郁闷了,对于Dictionary<TKey, TValue>来说,实现System.IEquatable<T>其实没什么用,始终还是要重写 Object.Equals(Object) 和 GetHashCode。

         有关的文章可以看这两篇:

         1、http://www.joycode.com/vbcti/archive/2009/02/20/115473.joy

         2、http://www.cnblogs.com/ldp615/archive/2009/09/05/1560791.html

    例如:

     public class MyComparer : IEqualityComparer<CustomerState>
    {
    public bool Equals(CustomerState x, CustomerState y)
    {
    return (x.Id == y.Id);
    }

    public int GetHashCode(CustomerState obj)
    {
    return obj.Id;
    }
    }


     

  • 相关阅读:
    E. Gosha is hunting (dp + wqs套wqs)
    【Codeforces Round #575 (Div. 3) 】 RGB Substring (hard version) ( FFT)
    C
    poj 1160 Post Office(dp + wqs二分)
    【 2018南京 】Magic Potion (网络流)
    【 2018南京 】Kangaroo Puzzle (思维+暴力模拟)
    【 2018南京 】Country Meow (模拟退火)
    【2018焦作网络赛】 Jiu Yuan Wants to Eat (熟练剖分 + 思维)
    【2018焦作网络赛】 Modular Production Line(费用流)
    【2018焦作网络赛】 B. Mathematical Curse (dp)
  • 原文地址:https://www.cnblogs.com/liyuxin/p/2315511.html
Copyright © 2011-2022 走看看