Welcome to Pete Brown's 10rem.net

First time here? If you are a developer or are interested in Microsoft tools and technology, please consider subscribing to the latest posts.

You may also be interested in my blog archives, the articles section, or some of my lab projects such as the C64 emulator written in Silverlight.

(hide this)

Nullable types and IComparable in the VS 2005 August CTP

Pete Brown - 08 September 2005

By now, you have likely read Somasegar's blog entry on nullable types in VS 2005.

You know that nullable types are now recognized by the CLR and no longer implement INullableValue. What you may not have realized is that nullable types no longer implement IComparable. The problem this introduces is that there appears to be no way to refer to value, nullable, and reference types generically for comparison. In particular, I'm working on an object model which includes dirty state tracking and similar functionality. In the base class, I have the following generic method:

protected void SetProperty<T>(ref T currentPropertyValue, T newValue) where T : IComparable

Inside, the code does a .CompareTo, checks the result, and then if different, sets the currentPropertyValue to the newValue, raises an event and sets the dirty and valid flags. You cannot pass a nullable type into that method as nullable types do not implement IComparable. It will take regular ints, strings, classes that implement IComparable, etc., but will not take nullable types.

You could simply remove the constraint, and do a != check for equality, but that produces a compiler error.

protected void SetProperty<T>(ref T currentPropertyValue, T newValue)

You get a compile error even if you impose a constraint of value type on the generic:

protected void SetProperty<T>(ref T currentPropertyValue, T newValue) where T : struct

 

Another option would be to ignore the IComparable interface, and simply do a .Equals inside the code. That also does not work in all cases, as you would need to make sure .Equals is overridden in the inherited classes. While you can impose that on your developers by policy, .Equals comes by default and does reference equality checking whereas IComparable requires a developer to explicitly implement the interface and add in the correct code for value equality checking. The former is easy to do, but is also very easy to forget and hard to debug if missed. The latter is preferred as it really says to the world that my object supports comparison checking.

 

Another option would be to keep the IComparable version, but add a second version that would handle only null types:

protected void SetProperty<T>(ref T currentPropertyValue, T newValue) where T : IComparable

protected void SetProperty(ref INullableValue currentPropertyValue, INullableValue newValue)

...except INullableValue no longer exists. This also produces a compile error:

protected void SetProperty(ref Nullable currentPropertyValue, Nullable newValue)

And this final attempt brings us back to the .Equals() problem:

protected void SetProperty(ref object currentPropertyValue, object newValue)

And so on and so on. The root problem here is that you cannot refer to a nullable type in a generic way in the August CTP, and you can't include nullable types in any group which must be IComparable.

I'm open to ideas, feel free to comment below.

 
posted by Pete Brown on Thursday, September 8, 2005
filed under:  

Comment on this Post

Remember me

2 trackbacks for “Nullable types and IComparable in the VS 2005 August CTP”

  1. Dinesh's Cyberstationsays:
    Our VP, Soma posted about the last minute changes to Nullable&lt;T&gt; in Visual Studio 2005. The changes...
  2. Pete Brown's Blogsays:
    If you recall from yesterday's blog entry, I was having some problems trying to find a way to compare...