In the interests of making code as usable as possible, interfaces and delegates with generic parameters should use the ``++out++`` and ``++in++`` modifiers when possible to make the interfaces and delegates covariant and contravariant, respectively.
The ``++out++`` keyword can be used when the type parameter is used only as a return type in the interface or delegate. Doing so makes the parameter covariant, and allows interface and delegate instances created with a sub-type to be used as instances created with a base type. The most notable example of this is ``++IEnumerable<out T>++``, which allows the assignment of an ``++IEnumerable<string>++`` instance to an ``++IEnumerable<object>++`` variable, for instance.
The ``++in++`` keyword can be used when the type parameter is used only as a method parameter in the interface or a parameter in the delegate. Doing so makes the parameter contravariant, and allows interface and delegate instances created with a base type to be used as instances created with a sub-type. I.e. this is the inversion of covariance. The most notable example of this is the ``++Action<in T>++`` delegate, which allows the assignment of an ``++Action<object>++`` instance to a ``++Action<string>++`` variable, for instance.
\[~tamas.vajk] note that the description I've written is for the "me" from last week. If it states too much of what is obvious to C# developers, please let me know what should be eliminated.
=== on 20 Jul 2015, 12:20:09 Tamas Vajk wrote:
\[~ann.campbell.2] I think the description is okay. We could shorten it, but it's not necessary. ``++in++`` and ``++out++`` is not used too often, so it's not necessarily common knowledge.
I've modified the description a bit. ``++IComparer++`` is not the most notable example for ``++in++`` generic arguments. We haven't discussed this, but this rule also applies for delegates with generic parameters. And the most notable example for ``++in++`` is the ``++Action++`` delegate: \https://msdn.microsoft.com/en-us/library/018hxwa8(v=vs.110).aspx
A side note: the most notable example of having both ``++in++`` and ``++out++`` is probably the ``++Func<T, TResult>++`` delegate: \https://msdn.microsoft.com/en-us/library/bb549151(v=vs.110).aspx
=== on 20 Jul 2015, 14:09:21 Ann Campbell wrote:
Thanks [~tamas.vajk]. Note that I've just worked covariant/contravariant into the description in the appropriate places. I suddenly realized we described them but didn't actually attach the descriptions to the words!