I have the following classes:
public abstract class ThingBase { }
public class ThingA : ThingBase { }
And the following generic class:
public class ThingOwner<ThingType> where ThingType : ThingBase { }
I would like to create a ThingOwner instance like below:
ThingOwner<ThingBase> thingOwner = new ThingOwner<ThingA>();
With this code, I get the following error: "Cannot implicitly convert type 'ThingOwner(ThingA)' to 'ThingOwner(ThingBase)'" .
I can't figure how to make it work. I know there are lots of existing discussions about generic classes and inheritance but I tried pretty much everything and I couldn't find a solution that worked for me.
Thanks!
You should make use of covariance for generic types introduced in C# 4.0. For this to work you need to use an interface instead of a class:
public interface IThingOwner<out ThingType> where ThingType : ThingBase { }
public class ThingOwner<ThingType> : IThingOwner<ThingType>
where ThingType : ThingBase
{
}
IThingOwner<ThingBase> thingOwner = new ThingOwner<ThingA>();
Covariance/contravariance is only supported for interfaces. If you need classes, then only these can work:
ThingOwner<ThingBase> thingOwner = new ThingOwner<ThingBase>();
ThingOwner<ThingA> thingOwner = new ThingOwner<ThingA>();
In addition to the above answers some explanation. While your question can be understood, think of the following:
State you have a derived class that accepts a type parameter ClassA
. In the ThingOwner<ClassA>
it is only allowed to add an instance of a class that is or derives from ClassA
. When you cast that to ThingOwner<BaseClass>
it is suddenly allowed to add an instance of ClassB
which also derived from BaseClass
. This can harm your program and is actually wrong. This was why they invented generics in the first place.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.