2014-12-05 40 views
1

我如何可以调用使用反射一个可变参数的方法?像这样的:调用可变参数方法

public static void ArgsMethod(__arglist) 
{ 
    ArgIterator ai = new ArgIterator(__arglist); 
    while(ai.GetRemainingCount() > 0) 
    { 
     Console.WriteLine(TypedReference.ToObject(ai.GetNextArg())); 
    } 
} 

typeof(Program).GetMethod("ArgsMethod").Invoke(null,new object[0])抛出NotSupportedException异常

+0

我怀疑你需要'TypedReference'。 – SLaks 2014-12-05 16:05:36

+0

调用传递方法名称和方法参数类型数组的GetMethod。对于可变参数方法,类型是一个Object数组。 – 2014-12-05 16:06:38

+0

@Max 1)'GetMethod(字符串,类型[])'仅检查固定的参数类型,它不创建基于可变参数类型的方法。 2)它宁愿是一个空的Type数组,因为我不会传递任何对象给方法。 – IllidanS4 2014-12-05 16:14:31

回答

3

由于RuntimeMethodInfo根本不支持这一(它明确地检查并抛出,如果该方法的调用约定VarArgs),你必须写一个包装,把一个正Object[],调用该方法生成IL,并调用它。 ILGenerator确实支持可变参数的方法,通过EmitCall。 MSDN甚至有足够的帮助有a sample that demonstrates this exact scenario

当然,这并不完全是方便,但然后没有关于可变参数是真的。

2

我不知道这是你想要的东西,但是这个工作对我来说;

class Program 
    { 
     public static void ArgsMethod(params object[] args) 
     { 
      foreach (var par in args) 
      { 
       Console.WriteLine("variable has type: " + par.GetType()); 

      } 
     } 

     static void Main(string[] args) 
     { 
      Type[] types = new Type[1]; 
      types[0] = typeof(object[]); 
      MethodInfo m = typeof(Program).GetMethod("ArgsMethod", types); 
      object[] parameters = new Object[1]; 
      parameters[0] = args; 
      m.Invoke(null, parameters); 
     } 
    } 

params不是__arglist同样的事情,但如果你在下发展C#中的方法,可以更好地使用PARAMS。

请参阅http://bartdesmet.net/blogs/bart/archive/2006/09/28/4473.aspx

+0

'__arglist'不是'params'。 – IllidanS4 2014-12-05 16:50:46