2

在深入的 C# 中,Jon Skeet 使用IEquatable<>重写重载操作Equals()

public sealed class Pair<T1, T2> : IEquatable<Pair<T1, T2>>
{
    public bool Equals(Pair<T1, T2> other)
    {
       //...
    }
}

他说我们这样做“是为了提供一个强类型的 API,以避免不必要的执行时检查”。

避免了哪些执行时间检查?更重要的是,实现一个接口是如何实现强类型API的呢?

在这本书的上下文中,我可能遗漏了一些东西。我认为接口通过多态性给了我们代码重用。我也明白它们有利于编程到抽象而不是具体类型。这就是我所知道的。

4

5 回答 5

5

默认Equals方法以 anobject作为参数。因此,在实现此方法时,您必须在代码中进行运行时检查以确保此对象是类型Pair(在您可以比较这两个之前):

public override bool Equals(Object obj) {
    // runtime type check here
    var otherPair = obj as Pair<T1, T2>;
    if (otherPair == null)
        return false;

    // comparison code here
    ...
}

然而,的Equals方法将 a作为类型参数。因此,您可以避免在您的实现中进行检查,从而提高效率:IEquatable<T>Pair<T1,T2>

public bool Equals(Pair<T1, T2> other)    
{    
    // comparison code here
    ...
}    

诸如 、 和 之类的类Dictionary<TKey, TValue>足够List<T>聪明LinkedList<T> ,可以使用IEquatable<T>.Equals而不是object.Equals在它们的元素上使用(如果可用)(请参阅MSDN)。

于 2012-05-03T13:19:08.467 回答
3

在这种情况下,他提供了 的强类型版本Object.Equals,它将替换可能如下所示的代码:

public override bool Equals(object other)
{
    // The following type check is not needed with IEquatable<Pair<T1, T2>>
    Pair<T1, T2> pair = other as Pair<T1, T2>;
    if (pair != null)
    {
        // <-- IEquatable<Pair<T1, T2>> implementation
    }
    else
    {
        return base.Equals(other);
    }
}
于 2012-05-03T13:19:21.357 回答
2

该接口提供了该方法的IEquatable<T>强类型实现,与接收.EqualsEqualsSystem.ObjectSystem.Object

于 2012-05-03T13:19:11.183 回答
0

我认为乔恩说“强类型”是指泛型。

我还没有找到非通用IEquitable接口,但IComparable<T>存在IComparable

于 2012-05-03T13:17:17.800 回答
0

公平地说,Skeet(尽管他肯定很快就会加入)他确实花时间讨论了第 2.2.1 节中“强类型”的含义。

在您的问题的上下文中(我的版本中的第 85 页)),我认为他的意思是默认的 Equals 方法(它将对象作为参数)遵循实现接口的强类型 Equals 方法。

于 2012-05-03T13:27:25.020 回答