I\'ve got the following code:
public static T GetCar() where T : ICar
{
T objCar = default(T);
if (typeof(T) == typeof(SmallCar)) {
Your code is illegal because while you might be testing and know that your given T is BigCar or some other such type, the compiler cannot know that in advance and therefore the code is illegal. Based upon your given usage, you could have
public static T GetCar<T>() where T : ICar, new()
{
return new T();
}
The new()
constraint allows you to invoke the default (parameterless) constructor on a type.
You can simplify your code
public static T GetCar<T>()
where T : ICar, new()
{
return new T();
}
Generics is a run-time concept. Information of the types used in a generic data type regardless if its a value or reference type can be obtained at run-time using reflection.
When a code with T is compiled into MSIL it only identifies it as having a type parameter. Therefore generic type parameter T is not known at compile-time.
class Program
{
static void Main(string[] args)
{
ICar smallCar = Helper.GetCar<SmallCar>("car 1");
ICar mediumCar = Helper.GetCar<MediumCar>("car 2");
Console.ReadLine();
}
}
static class Helper
{
public static T GetCar<T>(string carName) where T : ICar
{
ICar objCar = default(T);
if (typeof(T) == typeof(SmallCar))
{
objCar = new SmallCar { CarName = carName };
}
else if (typeof(T) == typeof(MediumCar))
{
objCar = new MediumCar { CarName = carName };
}
return (T)objCar;
}
}
interface ICar
{
string CarName { get; set; }
}
class SmallCar : ICar
{
public string CarName { get; set ; }
}
class MediumCar : ICar
{
public string CarName { get; set; }
}
You cannot convert to T
because of the fact that T isn't known at compile time.
If you want to get your code to work you can change the return type to ICar
and remove the generic T
return type.
You also can cast to T
. This would work too.
If you only using the default constructor you can also constain on new()
and use new T()
to get your code to work.
public ICar GetCar<T>()
where T : ICar
{
ICar objCar = null;
if (typeof(T) == typeof(SmallCar)) {
objCar = new SmallCar();
} else if (typeof(T) == typeof(MediumCar)) {
objCar = new MediumCar();
} else if (typeof(T) == typeof(BigCar)) {
objCar = new BigCar();
}
return objCar;
}
Cast:
public T GetCar<T>()
where T : ICar
{
Object objCar = null;
if (typeof(T) == typeof(SmallCar)) {
objCar = new SmallCar();
} else if (typeof(T) == typeof(MediumCar)) {
objCar = new MediumCar();
} else if (typeof(T) == typeof(BigCar)) {
objCar = new BigCar();
}
return (T)objCar;
}
New-constraint:
public T GetCar<T>()
where T : ICar, new()
{
return new T();
}