反射产生和泛型类型 [英] Reflection-generated and generic types

查看:138
本文介绍了反射产生和泛型类型的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有没有用 Reflection.Emit的另一个讨厌的时刻和类型的管理。



我说,我有一个名为的MyType A型这是在动态生成的程序集中定义。
呼叫 MyType.GetMethods()结果在引发NotSupportedException ,这我减少到写我自己的一套的包装和查找表。然而,当我打电话同样是发生的getMethods()或在其上用自己的类型作为参数的通用标准泛型类型的任何其他方法反思:




  • 元组LT; INT,串> =>工作正常

  • 元组LT; INT,MyType的> =>例外



我可以得到从泛型类型定义方法列表:



的typeof(元组LT; INT,的MyType).GetGenericTypeDefinition()的getMethods()



然而,这些方法具有通用占位符,而不是实际值(如 T1 TResult 等),我不喜欢写另一个杂牌跟踪此通用参数回原来的值。



一个的代码示例:

  VAR asmName =新的AssemblyName(测试); 
访问var = AssemblyBuilderAccess.Run;
VAR ASM = AppDomain.CurrentDomain.DefineDynamicAssembly(asmName,访问);
VAR模块= asm.DefineDynamicModule(测试);

VAR ATYPE = module.DefineType(A);
VAR tupleType = typeof运算(元组LT;,>);
VAR元组= tupleType.MakeGenericType(新[] {typeof运算(INT),ATYPE});

tuple.GetProperty(项目1); //< - 这里的错误



所以,问题是:




  1. 如何检测如果一个类型是安全的,叫的getMethods()
  2. 如何获得方法的实际列表和它们的通用参数值,如果该类型是不是安全?


解决方案

我在跟进质询有了答案。在 TypeBuilder 类有一堆静态重载这些方法都完成的事情:

  VAR genericTuple = typeof运算(元组LT;,>); 
VAR myTuple = genericTuple.MakeGenericType(typeof运算(INT)的myType);
VAR男星= TypeBuilder.GetConstructor(myTuple,genericTuple.GetConstructors()一());



奇怪的是,没有的getProperty 过载。然而,财产getter和setter仍然可以使用解决 GetMethod

  VAR genericGetter = typeof运算(元组LT;,>)的getProperty(项目1)GetMethod。; 
VAR实际= TypeBuilder.GetMethod(myTuple,genericGetter);


I'm having yet another nasty moment with Reflection.Emit and type management.

Say, I have a type named MyType which is defined in the dynamically generated assembly. Calling MyType.GetMethods() results in a NotSupportedException, which has reduced me to writing my own set of wrappers and lookup tables. However, the same is happening when I'm calling GetMethods() or any other introspecting methods on standard generic types which use my own types as generic arguments:

  • Tuple<int, string> => works fine
  • Tuple<int, MyType> => exception

I can get the method list from the generic type definition:

typeof(Tuple<int, MyType).GetGenericTypeDefinition().GetMethods()

However, the methods have generic placeholders instead of actual values (like T1, TResult etc.) and I don't feel like writing yet another kludge that traces the generic arguments back to their original values.

A sample of code:

var asmName = new AssemblyName("Test");
var access = AssemblyBuilderAccess.Run;
var asm = AppDomain.CurrentDomain.DefineDynamicAssembly(asmName, access);
var module = asm.DefineDynamicModule("Test");

var aType = module.DefineType("A");
var tupleType = typeof(Tuple<,>);
var tuple = tupleType.MakeGenericType(new [] { typeof(int), aType });

tuple.GetProperty("Item1"); // <-- here's the error

So the questions are:

  1. How do I detect if a type is safe to call GetMethods() and similar methods on?
  2. How do I get the actual list of methods and their generic argument values, if the type is not safe?

解决方案

I got an answer in a follow-up question. The TypeBuilder class has a bunch of static overloads which do exactly the thing:

var genericTuple = typeof(Tuple<,>);
var myTuple = genericTuple.MakeGenericType(typeof(int), myType);
var ctor = TypeBuilder.GetConstructor(myTuple, genericTuple.GetConstructors().First());

Strangely, there's no overload of GetProperty. However, property getters and setters can still be resolved using GetMethod:

var genericGetter = typeof(Tuple<,>).GetProperty("Item1").GetMethod;
var actual = TypeBuilder.GetMethod(myTuple, genericGetter);

这篇关于反射产生和泛型类型的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆