如何从反射的上下文中调用泛型方法?

时间:2012-08-08 11:30:43

标签: c# generics reflection

我有一个Constraints对象,它将获得一组其他对象必须遵守的规则。

constraints有一个名为GetEnumValueRange<T>()的方法,其中T是一种枚举类型。

例如,我可以将枚举定义为:

[Flags]
public enum BoxWithAHook
{
    None = 0,
    Thing1 = 1,
    Thing2 = 2,
    ...
    // lots of other things that might be in the box
    ThingN = N
}

然后我可以获得一系列在BoxWithAHook的给定上下文中有效的值:

var val = constraints.GetEnumValueRange<BoxWithAHook>();    

问题在于我正在尝试使用反射来完成这项工作。我无法指定类型为BoxWithAHook,因为它可能是任何扩展Enum的内容。这是我的一个例子:

if (propertyInfo.PropertyType.BaseType == typeof(Enum))
{
    var val = constraints.GetEnumValueRange<>(); // what is the generic type here?

    // now I can use val to get the constraint values
}

我可以指定泛型类型吗?理想情况下,这可行:

constraints.GetEnumValueRange<propertyInfo.PropertyType>(); 

但显然不是

2 个答案:

答案 0 :(得分:2)

您可能需要通过MethodInfo进行一些反思:

if (propertyInfo.PropertyType.BaseType == typeof(Enum))
{
    MethodInfo method = typeof(Constraints).GetMethod("GetEnumValueRange");
    MethodInfo genericMethod = method.MakeGenericMethod(propertyInfo.PropertyType);
    var val = genericMethod.Invoke(constraints, null);

    // ...
}

答案 1 :(得分:1)

为什么不对GetEnumValueRange进行重载,这需要一个Type参数,所以你最终会得到这样的结果:

public class Constraints
{
    public IEnumerable GetEnumValueRange(Type enumType)
    {
        // Logic here
    }

    public IEnumerable<T> GetEnumValueRange<T>()
    {
        return GetEnumValueRange(typeof(T)).Cast<T>();
    }
}

然后你可以简单地使用constraints.GetEnumValueRange(propertyInfo.PropertyType),如果有像这样的可用替代品,我个人会避免反思。