C# language feature:

  • Generic co- and contravariance

applies to

  • interfaces and delegates utilizing generics

benefit

  • 1) Co-variance allows assignment compatibility between parent and child relationship during dynamic polymorphism. i.e. base can be assigned derived/decendent class type.
  • 2) Contra-variance allows assignment compatibility of type specified or less derived/antecedent class type.

how to use

  • Use out modifier preceding type for co-variance, use in modifier for contra-variance.

see also

  • Co- and Contra-variance for delegates

example:

        class Base { }
 
        class Derived : Base { }

        class gernericvariance
        {
            delegate T Func<out T>();
            delegate void Action<in T>(T a);
 
            static void variance(string[] args)
             {
                // Covariance
                Func<Derived> Derived = () => new Derived();  // Declare a delegate with return type defined as derived type (specified generic value)
                Func<Base> Base = Derived;  // Declare a delegate with return type defined base type and assign the derived delegate 
                                            // (which can be substituted where base is used, i.e. this is generic Covariance) 

                // Contravariance
                Action<Base> basedel = (baseobj) => { Console.WriteLine(baseobj); };  // Declare a delegate with defined base type as parameter (specified generic value)
                Action<Derived> derivedel = basedel;    // Declare a delegate with defined derived type as parameter and assign the 
                                                        // base delegate (when delegate is called with derived parameter object, 
                                                        // this object can be substituted where base is expected.) This is generic Contravariance! 
            }
        }