如何通过反射调用通用方法

6

有没有可能使用反射调用具有“显式类型参数”<S>定义的方法,例如oObject.Cast<S>()

这里是:

IList <P> oObject = new List <P>();

我尝试了一下。
oObject.getType().InvokeMember( "Cast", BindingFlags.InvokeMethod, null, oObject, null)

但是它不起作用,有人知道为什么吗?


这里是完整的测试代码,但它仍然不起作用。最后一行总是会产生异常。有可能让它工作吗?

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Reflection;

namespace reflection_tester
{
    class CBase
    {
        public string Ja = "I am the base";
    }

    class MyClass01 : CBase
    {
        public string _ID;

        public string ID
        {
            get { return _ID; }
            set { _ID = value; }
        }
    }

    class Program
    {

        public static object wrapper()
        {
            //return a list of classes MyClass01

            IList<MyClass01> lstClass01 = new List<MyClass01>();

            MyClass01 oClass01a = new MyClass01();
            oClass01a.ID = "1";

            MyClass01 oClass01b = new MyClass01();
            oClass01b.ID = "2";

            lstClass01.Add(oClass01a);
            lstClass01.Add(oClass01b);

            return lstClass01;
        }

        static void Main(string[] args)
        {

            MyClass01 oMy1 = new MyClass01();
            oMy1._ID = "1";

            MyClass01 oMy2 = new MyClass01();
            oMy2._ID = "3";

            IList<MyClass01> oListType01 = new List<MyClass01>();

            oListType01.Add(oMy1);
            oListType01.Add(oMy2);

            object oObjectType = new object();

            oObjectType = oListType01;

            /* this works */
            IEnumerable<CBase> enumList = oListType01.Cast<CBase>();

            MethodInfo mInfo = typeof(System.Linq.Enumerable).GetMethod("Cast", new[] { typeof(System.Collections.IEnumerable) }).MakeGenericMethod(typeof(CBase));

            /* this does not work, why ? throws exception */
            IEnumerable<CBase> enumThroughObject = (IEnumerable<CBase>)mInfo.Invoke(oObjectType, null);

            return;
        }
    }
}
2个回答

16

Cast扩展方法属于Enumerable类,你需要调用MakeGenericMethod方法:

typeof(System.Linq.Enumerable)
    .GetMethod("Cast", new []{typeof(System.Collections.IEnumerable)})
    .MakeGenericMethod(typeof(S))
    .Invoke(null, new object[] { oObjectType })

更新: 由于该方法是静态的,因此Invoke的第一个参数应该为null


调用函数不接受一个参数,所以如果我将第二个参数设置为“null”,就会出现异常。有什么线索吗? - milan
1
@milan:抱歉,看起来@Rob的代码略有错误。根据MSDN,您应该调用.Invoke(null, oObject),因为Cast是静态的。http://msdn.microsoft.com/en-us/library/a89hcwhh.aspx - user7116
请看下面的评论,它仍然不起作用... - milan
它应该是 .Invoke(null, oObject) 而不是 .Invoke(oObject, null) - Rob Fonseca-Ensor
谢谢,米兰。我会更新我的回答。 - Rob Fonseca-Ensor
显示剩余7条评论

0

3
抱歉,我不理解这样简短的说明,请您提供一些代码以便更好地理解。 - milan

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