在运行时,我不知道变量v1
是什么类型。出于这个原因,我编写了许多if else
语句:
if (v1 is ShellProperty<int?>)
{
v2 = (v1 as ShellProperty<int?>).Value;
}
else if (v1 is ShellProperty<uint?>)
{
v2 = (v1 as ShellProperty<uint?>).Value;
}
else if (v1 is ShellProperty<string>)
{
v2 = (v1 as ShellProperty<string>).Value;
}
else if (v1 is ShellProperty<object>)
{
v2 = (v1 as ShellProperty<object>).Value;
}
唯一的区别是在ShellProperty<AnyType>
。
所以,而不是用很多if else
语句来写这个,我决定使用反射来获得运行时的属性类型:
Type t1 = v1.GetType().GetProperty("Value").PropertyType;
dynamic v2 = (v1 as ShellProperty<t1>).Value;
这段代码获得v1
的PropertyType
并将其分配给局部变量t1
,但在此之后,我的编译器说:
t1是一个变量,但像类型
一样使用
所以它不允许我在ShellProperty<>
里面写t1
。
请告诉我如何解决这个问题,以及如何获得比我拥有的更紧凑的代码。我需要创建一个新类吗?
你离MakeGenericType
很近了,你只是错过了一个电话。
我相信你的代码应该是这样的:
Type t1 = v1.GetType().GetProperty("Value").PropertyType;
var shellPropertyType = typeof(ShellProperty<>);
var specificShellPropertyType = shellPropertyType.MakeGenericType(t1);
dynamic v2 = specificShellPropertyType.GetProperty("Value").GetValue(v1, null);
编辑:正如@PetSerAl指出的那样,我添加了一些不必要的间接层。对不起,OP,您可能需要像这样的一行符:
dynamic v2 = v1.GetType().GetProperty("Value").GetValue(v1, null);
对于泛型,您必须动态创建它们。
MethodInfo method = typeof(Sample).GetMethod("GenericMethod");
MethodInfo generic = method.MakeGenericMethod(myType);
generic.Invoke(this, null);
创建泛型对象,可以使用
var type = typeof(ShellProperty<>).MakeGenericType(typeof(SomeObject));
var v2 = Activator.CreateInstance(type);
请参考从c#类型变量初始化泛型变量