Delegate-contravariance (parameter compatibility)
I'm looking at the text C# 5 in a Nutshell
, Delegate Parameter Compatibility section. It says:
When you call a method, you can provide arguments with more specific types than the parameters of that method. This is common polymorphic behavior. For the same reason, a delegate can have more specific parameter types than its target. This is called contravariance.
This paragraph makes sense right down to the last judgment. Why is this contravariance, i.e. Which projection is contravariant here?
Below is the following example.
delegate void StringAction (string s);
class Test
{
static void Main()
{
StringAction sa = new StringAction (ActOnObject);
sa ("hello");
}
static void ActOnObject (object o)
{
Console.WriteLine (o); // hello
}
}
source to share
The projection object
(function parameter ActionObject
) onto the type declared for the delegate ( string
) is contravariant.
This is allowed because by passing it a string (which must be associated with the signature of the delegate), you are guaranteed to have object
(which the assigned function assigns), so everything is fine and safe.
As you know, "normal polymorphism" in this context is actually called covariance .
See MSDN for details .
source to share
Function types are contravariant in argument types. In your example, the type
delegate void ObjectAction(object o);
is a subtype
delegate void StringAction(string s);
as ObjectAction
can be used wherever used StringAction
, because if the caller passes an argument string
, the argument must also be of type object
.
object
is a supertype string
but ObjectAction
is a subtype StringAction
; subtyping goes in the opposite direction. This is why it is called contravariant. Because changing function subtypes goes in the opposite direction of parameter subtypes.
source to share