2

I've read in several articles that

for reference types using IEquatable reduces the use of casting

Can someone kindly provide a convincing example.

Linger
  • 14,942
  • 23
  • 52
  • 79

3 Answers3

2

Just to add a simple example after Dario's explanation:

class Person : IEquatable<Person>
{
    public string Name { get; set; }

    public override bool Equals(object obj)
    {
        if (obj is Person)
        {
            Person other = (Person)obj;
            // check equality
        }
        return base.Equals(obj);
    }

    #region IEquatable<Person> Members

    public bool Equals(Person other)
    {
        // check equality without cast
    }

    #endregion
}

Note: This is just a little fragment that shows why this avoids a cast. For a correct implementation check the docs:

If you implement IEquatable<(Of <(T>)>), you should also override the base class implementations of Object..::.Equals(Object) and GetHashCode so that their behavior is consistent with that of the IEquatable<(Of <(T>)>)..::.Equals method

Community
  • 1
  • 1
bruno conde
  • 47,767
  • 15
  • 98
  • 117
  • You could just drop IEquatable from the class definition and the methods will still work the same way. So I don't see how IEquatable in itself reduces casting here. Help! –  May 20 '09 at 16:56
  • For example, if your implementing some kind of a collection that is expected to contain lots of items, performance is an important factor. In this case, you can request that all your items implement IEquatable that offers slightly better performance. This way, important compare methods that can be called *trillions* of times can at lest avoid the cast in the Equals in each comparation. – bruno conde May 20 '09 at 17:19
  • @Bruno: I see! I had a quick peek at List.Contains. This creates a Comparer which will use the implementation of IEquatable if the type implements it. Thanks, you've been an imense help! Nickyt's post also helped me get my head round this. Thanks guys! –  May 20 '09 at 18:36
  • Note that one should only implement `IEquatable` for structs or sealed class types. It can offer a big performance win when used for structs, and a smaller win for sealed types. It should not be used with unsealed types, since the only way to make it work correctly with derived types that override `Object.Equals` is to have the implementation of `IEquatable.Equals(T)` call the virtual `Object.Equals(Object)` method, which is what would happen in its absence. – supercat Sep 17 '12 at 16:46
1

Do you know this article? It says

If you want to have your own implementation, you can override this method. Since the Equals method has a parameter of type Object, a cast will be needed in order to be able to access class specific members.

This is where the IEquatable interface comes in. The IEquatable is a new generic interface in .NET 2.0 that allows you to do the same as the System.Object.Equals method but without having to perform casts. So, when implementing this interface, you can reduce the number of casts, which is a good thing for performance. Especially when working a lot with generic collections, since generic collections make use of this equality comparison in some of their methods (List.Equals(), List.IndexOf(), List.LastIndexOf(), ...).

Due to its generic type parameter, IEquatable<T> can provide type-checking at compiletime so you don't have to cast and late-bind with objects.

Community
  • 1
  • 1
Dario
  • 48,658
  • 8
  • 97
  • 130
0

I believe your answer is here, http://msdn.microsoft.com/en-us/library/ms131190.aspx. Read the remarks section on the page.

nickytonline
  • 6,855
  • 6
  • 42
  • 76
  • While this may theoretically answer the question, [it would be preferable](http://meta.stackexchange.com/q/8259) to include the essential parts of the answer here, and provide the link for reference. – Bill the Lizard Oct 31 '11 at 12:25