Introduction
Implementing the interfaces IComparable<T>
and IEquatable<T>
is often not as straightforward as it seems to be at first glance. With this tip I want to give you some help to automate this implementation as far as possible by using snippets in Visual Studio.
Background
Microsoft defines some guidelines for implementing operators or certain interfaces. The interfaces I had to implement often were IEquatable<T>
and IComparable<T>
. Experience has taught me that the implementation mostly leads into clerical errors because the correct implementations are relatively complex, moreover the implementations must differ between reference types and value types.
Here are some remarks that not listed completely but gives you an impression of the matters to consider:
- Implementing IEquatable<T> does implicitly require the implementation of the
==
and !=
operators (=
and <>
in VB) - Implementing
IComparable<T>
does implicitly require the implementation of the non generic IComparable
and of the comparison operators <
, >
, <=
and >=
. - Within the
Equal()
method you must not use the equality operators - because this would lead into an endless recursion - Whitin the operators you must not call
Equal()
to check whether an argument is null
or the query refence-equality - because this will lead into an endless recursion in some circumstances - In addition to the
Equal()
method of the interface the inherited Equal()
method as well as the method GetHashCode()
must be overridden - Within the overridden
Equal()
method the type of the specified argument must be checked to avoid an invalid cast exception
A complete list of all requirements can be found at the MSDN.
Using the Snippets
The appended file contains some code snippets for C# and Visual Basic that creates the code to implement the interfaces. Unzip the file and copy the snippets into the appropriate directories of your Visual Studio user settings, e.g. "<MyDocuments-folder>\Visual Studio 2010\Code Snippets\<Language>\My Code Snippets".
Whithin the editor (C# or VB) simply input the shortcut of the snippet you want and press [Tab]. As an example your class may look like this:
public class MyClass : IEquatable<MyClass>
{
}
To create the implementation for the interface just input "iequc" (IEquatable for Class) and press [Tab].
public class MyClass : IEquatable<MyClass>
{
iequc|
}
The result will be as follows:
public class MyClass : IEquatable<MyClass>
{
#region IEquatable<MyClass> Member
public override int GetHashCode()
{
return base.GetHashCode();
}
public override bool Equals( object obj )
{
return Equals(obj as MyClass);
}
public bool Equals( MyClass other )
{
if( ReferenceEquals(other, null) )
return false;
if( ReferenceEquals(this, other) )
return true;
throw new NotImplementedException();
}
public static bool operator ==( MyClass left, MyClass right )
{
if( ReferenceEquals(left, right) )
return true;
if( ReferenceEquals(left, null) )
return false;
return left.Equals(right);
}
public static bool operator !=( MyClass left, MyClass right )
{
if( ReferenceEquals(left, right) )
return false;
if( ReferenceEquals(left, null) )
return true;
return !left.Equals(right);
}
#endregion
}
The only line that must be edit is marked with "TODO". The comments should be edited at some parts (marked with "...") to help the clients that will use your class.
All snippets works this way. This means that all each snippet contains exactly one line of code that must be edited. It is always the line that finally does the comparision. All snippets creates the necessary comments that may be adjusted in places.
For beginners: All shortcuts as well as the snippets itself can be modified to fit your own requirements. Just open a snippet within the editor to see how it works. E.g. to modify the shortcut search for the "Shortcut" element and edit its content.