می دونیم که در C# :
اگر
class Drived : Base {}
آنگاه
Base base=new Drived();
ولی در جنریک نمی تونیم تایپ ها رو به جای هم استفاده کنیم مگر اینکه از Covariance یا Contravariance استفاده کنیم
اگر می خوای بتونی یک متغیر از جنس اینترفیس/دلیگیت جنریک رو به متغیر دیگری از همون اینترفیس/دلیگیت با تایپ بالاتر تبدیل کنی در تعریف جنریک از عبارت out استفاده کن
نکته : در اون اینترفیس/دلیگیت نمی تونی هیچ ورودی از جنس اون تایپ داشته باشی
در واقع خروجی با تایپ پایین تر به تایپ بالاتر Cast خواهد شد
اگر :
public interface IEnumerable<out T> : System.Collections.IEnumerable
آنگاه :
IEnumerable<Derived> d = new List<Derived>();
IEnumerable<Base> b = d;
اگر می خوای بتونی یک متغیر از جنس اینترفیس/دلیگیت جنریک رو به متغیر دیگری از همون اینترفیس/دلیگیت با تایپ پایین تر تبدیل کنی در تعریف جنریک از عبارت in استفاده کن
نکته : در اون اینترفیس/دلیگیت نمی تونی هیچ خروجی از جنس اون تایپ داشته باشی
در واقع ورودی با تایپ پایین تر به تایپ بالاتر Cast خواهد شد
اگر :
public delegate void Action<in T>(T obj);
آنگاه :
Action<Base> b = (target) => { Console.WriteLine(target.GetType().Name); };
Action<Derived> d = b;