如何通过反射调用带有枚举(enum)参数的方法?

5

我需要调用以下方法:

public bool Push(button RemoteButtons)

RemoteButtons是这样定义的:

enum RemoteButtons { Play, Pause, Stop }

Push方法属于RemoteControl类。RemoteControl类和RemoteButton枚举都位于一个需要在运行时加载的程序集中。我可以通过以下方式加载程序集并创建RemoteControl实例:

Assembly asm = Assembly.LoadFrom(dllPath);
Type remoteControlType = asm.GetType("RemoteControl");
object remote = Activator.CreateInstance(remoteControlType);

现在,我该如何调用Push方法,因为它唯一的参数是一个枚举类型,我也需要在运行时加载它?

如果我使用C# 4,我会使用dynamic对象,但我使用的是C# 3/.NET 3.5,所以它不可用。


即使在C#4中,我也不会使用dynamic来实现这个。 - IAbstract
你说的“未知”枚举是什么意思? - Jon
我认为OP的意思是:enum RemoteButtons { Play, Pause, Stop } 如果我的理解正确,OP需要明确表达。 :) - IAbstract
我会有一个接口,例如 IRemoteControl,它公开了 bool Push(...) 并由通过反射实例化的类引用并由 RemoteControl 实现。这样,您就不必通过反射调用该方法。 - IAbstract
出于清晰起见,以下是有关编程的内容。 - ChrisB
2个回答

6
假设我有以下结构:
public enum RemoteButtons
{
    Play,
    Pause,
    Stop
}
public class RemoteControl
{
    public bool Push(RemoteButtons button)
    {
        Console.WriteLine(button.ToString());
        return true;
    }
}

然后,我可以使用反射来获取这些值,方法如下:
Assembly asm = Assembly.GetExecutingAssembly();
Type remoteControlType = asm.GetType("WindowsFormsApplication1.RemoteControl");
object remote = Activator.CreateInstance(remoteControlType);

var methodInfo = remoteControlType.GetMethod("Push");
var remoteButtons = methodInfo.GetParameters()[0];

// .Net 4.0    
// var enumVals = remoteButtons.ParameterType.GetEnumValues();

// .Net 3.5
var enumVals = Enum.GetValues(remoteButtons.ParameterType);

methodInfo.Invoke(remote, new object[] { enumVals.GetValue(0) });   //Play
methodInfo.Invoke(remote, new object[] { enumVals.GetValue(1) }); //Pause
methodInfo.Invoke(remote, new object[] { enumVals.GetValue(2) }); //Stop

我从方法中获取参数类型,然后从该类型获取枚举值。

不幸的是,GetEnumValues 似乎只在 .NET 4+ 中可用。我使用的是 3.5 版本。 - ChrisB
我接受这个答案,因为它提供了我需要的95%。我只做了一个小修改,以便代码可以在.NET 3.5中运行。 - ChrisB

1
以下代码可以正常工作!
asm = Assembly.LoadFrom(dllPath);
Type typeClass = asm.GetType("RemoteControl");
obj = System.Activator.CreateInstance(typeClass);
Type[] types = asm.GetTypes();
Type TEnum = types.Where(d => d.Name == "RemoteButtons").FirstOrDefault();
MethodInfo method = typeClass.GetMethod("Push", new Type[] { TEnum});
object[] parameters = new object[] { RemoteButtons.Play };
method.Invoke(obj, parameters);

请注意以下代码:“Type TEnum = types.Where(d => d.Name == "RemoteButtons").FirstOrDefault();” 您必须使用以下代码从程序集中获取Type。

但是不要直接使用 typeof(RemoteButtons) 来查找方法,像这样:" MethodInfo method = typeClass.GetMethod("Push", new Type[] { typeof(RemoteButtons) });" 这实际上不是相同的类型。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接