Andrew Stopford's Weblog

poobah

Sponsors

News

Articles

Family

Old Blogs

How about generics covariance/contravariance support in C# 3.0?

Spent a bit of time with Linq the last few days and one of things that has struck me is that Linq outputs a Linq query results to a generic IEnumerable type. If your application always has a understanding of the type that the generic type forms from this then your made up. However the trouble with generics in C# in general at the moment is that you can't cast a type down to it's base type. If you want a generic piece of code that needs to handle base types only (in Linq's case this could be the Table type that types inherit from in the generic IEnumerable type). This is where contravariance seems to help, Jeron has a great post on the fact that contravariance is supported by the CLR but it's not in C# yet. How about it Microsoft?

Update: I have adjusted the title of this post slightly, in the comments Frans as always makes a great point about the difference and includes a link. In my reply I have qouted directly for you to see the difference. Lets have both in C#.

Posted: Oct 03 2006, 04:54 PM by astopford | with 7 comment(s)
Filed under:

Comments

David Taylor said:

I have also run into a few issues where I though generics would be a solution, but ended up running into this same problem.

I would love it is this became possible.

However does it cause any problems when using value types as in:

List<object> list = new List<int>();

I would need to think through the ramifications, given the way the CLR implements generics.

# October 3, 2006 12:16 PM

FransBouma said:

IMHO this is called co-variance. Contravariance is the opposite:

http://blogs.msdn.com/rmbyers/archive/2005/02/16/375079.aspx

# October 3, 2006 2:18 PM

astopford said:

Frans, from reading that post types in generics in C# as it stands right now can be considerd invariant. Contravariance seems to be stricter on how types relate, to qoute:

it means that the subtype relationship of the generic type varies inversely with the relationship of the type parameter.  Or formally, G<T> is a subtype of G<U> if and only if U is a subtype of T.

Arrays in C# are already contravariant, to qoute.

For example, since you can convert a string to an object, shouldn’t you also be able to convert a List<string> to a List<object>?  After all, you can convert a string[] to an object[], why should List<T> be any different?

More formally, in C# v2.0 if T is a subtype of U, then T[] is a subtype of U[], but G<T> is not a subtype of G<U> (where G is any generic type).  In type-theory terminology, we describe this behavior by saying that C# array types are “covariant” and generic types are “invariant”.

# October 4, 2006 4:23 AM

Martin Z said:

Imho, the best way to add covariance and contravariance to generics would be to add "Readonly" and "WriteOnly" to the Type arguments.

That is ReadOnlyList<Readonly T> (in which no method in ReadOnlyList can be defined as taking an object of type T as an argument, nor can any return-value, out-parameter, or exception throw a Generic Object that involves type T except as Readonly.

ReadOnly would be the way to make sure you never have the type violation of trying to insert an "Object" into a list of "strings" because we're using List<string> in a variable typed as List<Object>.

WriteOnly is the opposite, and handles the reverse concept of substitution - cases where we want to treat a List<Object> as a List<String> - sine you can insert Strings into a list of OBjects, but you can't read strings _out_ of a list of Objects.

# October 20, 2006 5:34 PM

chris said:

I am writing to support this post.  Although I see the problems with implementing co-/contravariance, the ability to cast concrete/lower types to their abstract/base type as a whole object tree allows for very generic and flexible coding.  I am glad I found this page because I knew others had to share my frustration, but I didn't know what to search for.

Cheers.

# May 18, 2007 2:15 PM

Andrew Stopford's Weblog said:

It's that time of year again and a custom on my blog to look back at my predictions for this year, relect

# December 28, 2007 11:02 AM

Ed said:

In case anyone in a position of authority looks at this post, I support this feature; I ran into an issue that this would have solved. It would be a nice addition to a future version of C#!

# September 29, 2008 11:57 AM