The quick answer is that you can do what you ask by declaring a type parameter IAmB<T> as covariant , only if the type is used as the return type :
public interface IAmB<out T> where T : IAmA { T SomeMethod(string someparam); }
out T means that you can use a more specific type than the one specified in the restrictions.
You cannot use T as a parameter. The following commands will not compile:
public interface IAmB<out T> where T : IAmA { void SomeMethod(T someparam); }
From the documentation
You can use the covariance type parameter as the return value of a method belonging to the interface, or as the return type of a delegate. You cannot use a covariant type parameter as a general type constraint for interface methods.
This is not compiler complexity. Assuming you can declare a covariant method parameter, your list will contain some objects that cannot handle the IAmB<IAmA> parameter - they would expect to enter ClassA or more specific. Your code will compile but crash at runtime.
What begs the question - why do you want to use IAmB<ClassA> ?
You should think before using this, although there may be other, more suitable ways to solve your real problem. It is unusual to use a common interface that implements a particular type, but tries to use it as if it were implementing another interface.
You can check the MSDN documentation section on covariance and contravariance , as well as Eric Lippert and John Skeet's answers to this CO-question: the difference between covariance and contravariance
source share