TypeBuilder.CreateType Metódus

Definíció

Létrehoz egy Type objektumot az osztály számára. Az osztály CreateType mezőinek és metódusainak definiálása után a program meghívja az objektum betöltéséhez Type .

public:
 Type ^ CreateType();
public Type CreateType();
member this.CreateType : unit -> Type
Public Function CreateType () As Type

Válaszok

Az osztály új Type objektumát adja vissza.

Kivételek

A beágyazási típus nem lett létrehozva.

-vagy-

Ez a típus nem absztrakt, és absztrakt metódust tartalmaz.

-vagy-

Ez a típus nem absztrakt osztály vagy interfész, és metódustörzs nélküli metódussal rendelkezik.

Hibás címketartalom a következőben ILGenerator: Hívás nélkül MarkLabel(Label)definiált egy címkét.

A típus érvénytelen Microsoft köztes nyelv (MSIL) kódot tartalmaz.

-vagy-

Az ágcél 1 bájtos eltolással van megadva, de a cél 127 bájtnál nagyobb távolságra van az ágtól.

A típus nem tölthető be. Például egy metódust static tartalmaz, amely a hívási konvencióval rendelkezik HasThis.

Példák

Az alábbi kódpéldában bemutatja, hogyan definiálhat eseménykezelőt az AppDomain.TypeResolve eseményhez annak érdekében, hogy a CreateType metódus beágyazott típuson legyen meghívva a beágyazási típus hívása során CreateType .

using System;
using System.Reflection;
using System.Reflection.Emit;
using System.Threading;
using System.Text;
using System.Resources;
using System.Collections;
using System.IO;

internal class NestedEnum {
    internal static TypeBuilder enumType = null;
    internal static Type tNested = null;
    internal static Type tNesting = null;

    public static void Main(String[] args) {
    AssemblyName asmName = new AssemblyName();
    asmName.Name = "NestedEnum";
    AssemblyBuilder asmBuild = Thread.GetDomain().DefineDynamicAssembly(asmName, AssemblyBuilderAccess.RunAndSave);
    ModuleBuilder modBuild = asmBuild.DefineDynamicModule("ModuleOne", "NestedEnum.dll");

    // Hook up the event listening.
    TypeResolveHandler typeResolveHandler = new TypeResolveHandler(modBuild);
    // Add a listener for the type resolve events.
    AppDomain currentDomain = Thread.GetDomain();
    ResolveEventHandler resolveHandler = new ResolveEventHandler(typeResolveHandler.ResolveEvent);
    currentDomain.TypeResolve += resolveHandler;

    TypeBuilder tb = modBuild.DefineType("AType", TypeAttributes.Public);
    TypeBuilder eb = tb.DefineNestedType("AnEnum", TypeAttributes.NestedPublic | TypeAttributes.Sealed, typeof(Enum), null);
    eb.DefineField("value__", typeof(int), FieldAttributes.Private | FieldAttributes.SpecialName);
    FieldBuilder fb = eb.DefineField("Field1", eb, FieldAttributes.Public | FieldAttributes.Literal | FieldAttributes.Static);
    fb.SetConstant(1);

    enumType = eb;

    // Comment out this field.
    // When this field is defined, the loader cannot determine the size
    // of the type. Therefore, a TypeResolve event is generated when the
    // nested type is completed.
    tb.DefineField("Field2", eb, FieldAttributes.Public);

    tNesting = tb.CreateType();
    if (tNesting == null)
        Console.WriteLine("NestingType CreateType failed but didn't throw!");	

    try {
        tNested = eb.CreateType();
        if (tNested == null)
        Console.WriteLine("NestedType CreateType failed but didn't throw!");	
    }
    catch {
        // This is needed because you might have already completed the type in the TypeResolve event.
    }

    if (tNested != null) {
        Type x = tNested.DeclaringType;
        if (x == null)
        Console.WriteLine("Declaring type was null.");
        else
        Console.WriteLine(x.Name);
    }

    asmBuild.Save( "NestedEnum.dll" );

    // Remove the listener for the type resolve events.
    currentDomain.TypeResolve -= resolveHandler;
    }
}

// Helper class called when a resolve type event is raised.
internal class TypeResolveHandler
{
    private Module m_Module;

    public TypeResolveHandler(Module mod)
    {
    m_Module = mod;
    }

    public Assembly ResolveEvent(Object sender, ResolveEventArgs args)
    {
    Console.WriteLine(args.Name);
    // Use args.Name to look up the type name. In this case, you are getting AnEnum.
    try {
        NestedEnum.tNested = NestedEnum.enumType.CreateType();
    }
    catch {
        // This is needed to throw away InvalidOperationException.
        // Loader might send the TypeResolve event more than once
        // and the type might be complete already.
    }

    // Complete the type.		
    return m_Module.Assembly;
    }
}
Imports System.Reflection
Imports System.Reflection.Emit
Imports System.Threading
Imports System.Text
Imports System.Resources
Imports System.Collections
Imports System.IO

Friend Class NestedEnum
   Friend Shared enumType As TypeBuilder = Nothing
   Friend Shared tNested As Type = Nothing
   Friend Shared tNesting As Type = Nothing
   
   Public Shared Sub Main()
      Dim asmName As New AssemblyName()
      asmName.Name = "NestedEnum"
      Dim asmBuild As AssemblyBuilder = Thread.GetDomain().DefineDynamicAssembly(asmName, AssemblyBuilderAccess.RunAndSave)
      Dim modBuild As ModuleBuilder = asmBuild.DefineDynamicModule("ModuleOne", "NestedEnum.dll")
      
      ' Hook up the event listening.
      Dim typeResolveHandler As New TypeResolveHandler(modBuild)
      ' Add a listener for the type resolve events.
      Dim currentDomain As AppDomain = Thread.GetDomain()
      Dim resolveHandler As ResolveEventHandler = AddressOf typeResolveHandler.ResolveEvent
      AddHandler currentDomain.TypeResolve, resolveHandler 
      
      Dim tb As TypeBuilder = modBuild.DefineType("AType", TypeAttributes.Public)
      Dim eb As TypeBuilder = tb.DefineNestedType("AnEnum", TypeAttributes.NestedPublic Or TypeAttributes.Sealed, GetType([Enum]))
      eb.DefineField("value__", GetType(Integer), FieldAttributes.Private Or FieldAttributes.SpecialName)
      Dim fb As FieldBuilder = eb.DefineField("Field1", eb, FieldAttributes.Public Or FieldAttributes.Literal Or FieldAttributes.Static)
      fb.SetConstant(1)
      
      enumType = eb
      
      ' Comment out this field.
      ' When this field is defined, the loader cannot determine the size
      ' of the type. Therefore, a TypeResolve event is generated when the
      ' nested type is completed.
      tb.DefineField("Field2", eb, FieldAttributes.Public)
      
      tNesting = tb.CreateType()
      If tNesting Is Nothing Then
         Console.WriteLine("NestingType CreateType failed but didn't throw!")
      End If 
      Try
         tNested = eb.CreateType()
         If tNested Is Nothing Then
            Console.WriteLine("NestedType CreateType failed but didn't throw!")
         End If
      Catch
      End Try ' This is needed because you might have already completed the type in the TypeResolve event.
      
      If Not (tNested Is Nothing) Then
         Dim x As Type = tNested.DeclaringType
         If x Is Nothing Then
            Console.WriteLine("Declaring type is Nothing.")
         Else
            Console.WriteLine(x.Name)
         End If
      End If 
      asmBuild.Save("NestedEnum.dll")
      
      ' Remove the listener for the type resolve events.
      RemoveHandler currentDomain.TypeResolve, resolveHandler 
   End Sub
End Class


' Helper class called when a resolve type event is raised.
Friend Class TypeResolveHandler
   Private m_Module As [Module]
   
   
   Public Sub New([mod] As [Module])
      m_Module = [mod]
   End Sub
   
   
   Public Function ResolveEvent(sender As [Object], args As ResolveEventArgs) As [Assembly]
      Console.WriteLine(args.Name)
      ' Use args.Name to look up the type name. In this case, you are getting AnEnum.
      Try
         NestedEnum.tNested = NestedEnum.enumType.CreateType()
      Catch
      End Try ' This is needed to throw away InvalidOperationException.
      ' Loader might send the TypeResolve event more than once
      ' and the type might be complete already.
      
      ' Complete the type.		    
      Return m_Module.Assembly
   End Function 'ResolveEvent
End Class

Megjegyzések

Ha ez a típus beágyazott típus, a metódust a CreateType beágyazási típuson kell meghívni, mielőtt a beágyazott típusra meghívják.

Ha az aktuális típus hiányos típusból származik, vagy hiányos illesztőket implementál, hívja meg a CreateType metódust a szülőtípuson és a felülettípusokon, mielőtt meghívja az aktuális típusra.

Ha a beágyazási típus olyan mezőt tartalmaz, amely beágyazott típusként definiált értéktípus (például beágyazott típusként definiált enumerálási mező), a CreateType metódus meghívása a beágyazási típuson eseményt AppDomain.TypeResolve hoz létre. Ennek az az oka, hogy a betöltő nem tudja meghatározni a beágyazási típus méretét, amíg a beágyazott típus be nem fejeződik. A hívónak meg kell határoznia egy kezelőt az TypeResolve eseményhez a beágyazott típus definíciójának befejezéséhez a TypeBuilder beágyazott típust képviselő objektum meghívásávalCreateType. A jelen témakör kód példája bemutatja, hogyan definiálhat ilyen eseménykezelőt.

A rendszer csak egyszer hoz létre típust, függetlenül attól, hogy hányszor hívja meg a metódust CreateType . Minden hívás ugyanazt Type az objektumot adja vissza.

A következőre érvényes: