.net - 是否可以在将自身指定为泛型类型参数的同时发出从泛型类型派生的类型?

标签 .net generics reflection.emit

想象一下以下完全合法的类型层次结构:

class A<T> where T : A<T>
{
}

class B : A<B>
{
  public B():base(){}
}

我的问题是 A<> 的静态编译定义是否可以动态发出类型 B ?

问题是如何在 ModuleBuilder.DefineType 中指定父类型.

或者也许有另一种方法来产生这种类型,除了
  • 使用上述方法
  • 使用 CodeDom(这很像创建一个临时文件并将其传递给 csc.exe :-))

  • 编辑:
    类型B应该有显式的公共(public)默认构造函数调用从 A<B> 继承的默认构造函数.

    最佳答案

    您可以使用 ModuleBuilder.DefineType 的重载没有指定父类型,然后使用 TypeBuilder.SetParent将父级设置为递归类型的方法(使用类似 typeof(A<>).MakeGenericType(tb) 的参数,其中 tb 是您的 TypeBuilder,但我面前没有 C# 编译器)。

    编辑 - 这是一个工作示例,假设你有一个 ModuleBuilder mb .对于空的默认构造函数,您不需要使用 DefineConstructor方法;或者,您可以使用 DefineDefaultConstructor .不过,我已经包含了一个显式调用基本构造函数的示例,以防您想在其中添加一些额外的逻辑。

    TypeBuilder tb = mb.DefineType("B");
    Type AB = typeof(A<>).MakeGenericType(tb);
    tb.SetParent(AB);
    ConstructorInfo ctor = TypeBuilder.GetConstructor(AB, typeof(A<>).GetConstructor(new Type[] { }));
    ILGenerator ilg = tb.DefineConstructor(MethodAttributes.Public, CallingConventions.Standard, new Type[] { }).GetILGenerator();
    ilg.Emit(OpCodes.Ldarg_0);
    ilg.Emit(OpCodes.Call, ctor);
    ilg.Emit(OpCodes.Ret);
    Type t = tb.CreateType();
    

    关于.net - 是否可以在将自身指定为泛型类型参数的同时发出从泛型类型派生的类型?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1421149/

    相关文章:

    c# - 错误 "An entity object cannot be referenced by multiple instances of IEntityChangeTracker"

    c# - 创建 DynamicMethod 为属性赋值?

    c++ - 如何以编程方式检测 DLL 在 .NET 中是编译为 32 位还是 64 位?

    .net - 不用打印机打印?

    .net - Windows 窗体应用程序的默认字体

    java - 我们可以通过调用 class#newInstance() 创建类型化类的实例吗

    java - 没有警告的通用接口(interface)比较器

    c# - 如何获取自定义属性的通用集合

    .net - 当属性类型为 Int64 时,DynamicMethod 返回错误值

    c# - 执行 XmlDocument 类型的 CustomAttributeBuilder 时出错