次の方法で共有


ILGenerator.Emit メソッド

ジャスト イン タイム (JIT: Just In Time) コンパイラの MSIL (Microsoft Intermediate Language) ストリームに命令を書き込みます。

オーバーロードの一覧

指定された命令を命令のストリームに書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode)

[C#] public virtual void Emit(OpCode);

[C++] public: virtual void Emit(OpCode);

[JScript] public function Emit(OpCode);

命令の MSIL (Microsoft Intermediate Language) ストリームに、指定した命令と文字引数を書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, Byte)

[C#] public virtual void Emit(OpCode, byte);

[C++] public: virtual void Emit(OpCode, unsigned char);

[JScript] public function Emit(OpCode, Byte);

命令の MSIL (Microsoft Intermediate Language) ストリームに、指定したコンストラクタの指定した命令とメタデータ トークンを書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, ConstructorInfo)

[C#] public virtual void Emit(OpCode, ConstructorInfo);

[C++] public: virtual void Emit(OpCode, ConstructorInfo*);

[JScript] public function Emit(OpCode, ConstructorInfo);

命令の MSIL (Microsoft Intermediate Language) ストリームに、指定した命令と数値引数を書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, Double)

[C#] public virtual void Emit(OpCode, double);

[C++] public: virtual void Emit(OpCode, double);

[JScript] public function Emit(OpCode, double);

命令の MSIL (Microsoft Intermediate Language) ストリームに、指定したフィールドの指定した命令とメタデータ トークンを書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, FieldInfo)

[C#] public virtual void Emit(OpCode, FieldInfo);

[C++] public: virtual void Emit(OpCode, FieldInfo*);

[JScript] public function Emit(OpCode, FieldInfo);

命令の MSIL (Microsoft Intermediate Language) ストリームに、指定した命令と数値引数を書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, Short)

[C#] public virtual void Emit(OpCode, short);

[C++] public: virtual void Emit(OpCode, short);

[JScript] public function Emit(OpCode, Int16);

命令の MSIL (Microsoft Intermediate Language) ストリームに、指定した命令と数値引数を書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, Integer)

[C#] public virtual void Emit(OpCode, int);

[C++] public: virtual void Emit(OpCode, int);

[JScript] public function Emit(OpCode, int);

命令の MSIL (Microsoft Intermediate Language) ストリームに、指定した命令と数値引数を書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, Long)

[C#] public virtual void Emit(OpCode, long);

[C++] public: virtual void Emit(OpCode, __int64);

[JScript] public function Emit(OpCode, long);

指定された命令を MSIL (Microsoft Intermediate Language) ストリームに書き込み、位置を確定した後でラベルを格納する領域を残します。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, Label)

[C#] public virtual void Emit(OpCode, Label);

[C++] public: virtual void Emit(OpCode, Label);

[JScript] public function Emit(OpCode, Label);

指定された命令を MSIL (Microsoft Intermediate Language) ストリームに書き込み、位置を確定した後でラベルを格納する領域を残します。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, Label())

[C#] public virtual void Emit(OpCode, Label[]);

[C++] public: virtual void Emit(OpCode, Label[]);

[JScript] public function Emit(OpCode, Label[]);

指定された命令を MSIL (Microsoft Intermediate Language) ストリームに書き込み、その後ろに指定されたローカル変数のインデックスを書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, LocalBuilder)

[C#] public virtual void Emit(OpCode, LocalBuilder);

[C++] public: virtual void Emit(OpCode, LocalBuilder*);

[JScript] public function Emit(OpCode, LocalBuilder);

指定された命令を MSIL ストリームに書き込み、その後ろに指定されたメソッドのメタデータ トークンを書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, MethodInfo)

[C#] public virtual void Emit(OpCode, MethodInfo);

[C++] public: virtual void Emit(OpCode, MethodInfo*);

[JScript] public function Emit(OpCode, MethodInfo);

命令の MSIL (Microsoft Intermediate Language) ストリームに、指定した命令と文字引数を書き込みます。このメソッドは、CLS と互換性がありません。

[Visual Basic] Overloads Public Sub Emit(OpCode, SByte)

[C#] public void Emit(OpCode, sbyte);

[C++] public: void Emit(OpCode, char);

[JScript] public function Emit(OpCode, SByte);

命令の MSIL (Microsoft Intermediate Language) ストリームに、指定した命令とシグネチャ トークンを書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, SignatureHelper)

[C#] public virtual void Emit(OpCode, SignatureHelper);

[C++] public: virtual void Emit(OpCode, SignatureHelper*);

[JScript] public function Emit(OpCode, SignatureHelper);

命令の MSIL (Microsoft Intermediate Language) ストリームに、指定した命令と数値引数を書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, Single)

[C#] public virtual void Emit(OpCode, float);

[C++] public: virtual void Emit(OpCode, float);

[JScript] public function Emit(OpCode, float);

指定された命令を MSIL ストリームに書き込み、その後ろに指定された文字列のメタデータ トークンを書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, String)

[C#] public virtual void Emit(OpCode, string);

[C++] public: virtual void Emit(OpCode, String*);

[JScript] public function Emit(OpCode, String);

指定された命令を MSIL ストリームに書き込み、その後ろに指定された型のメタデータ トークンを書き込みます。

[Visual Basic] Overloads Public Overridable Sub Emit(OpCode, Type)

[C#] public virtual void Emit(OpCode, Type);

[C++] public: virtual void Emit(OpCode, Type*);

[JScript] public function Emit(OpCode, Type);

使用例

[Visual Basic, C#, C++] ジャンプ テーブルを持つ動的メソッドを作成する方法を次のコード例に示します。ジャンプ テーブルは、 Label の配列を使用して作成します。

[Visual Basic, C#, C++] メモ   ここでは、Emit のオーバーロード形式のうちの 1 つだけについて、使用例を示します。その他の例については、各オーバーロード形式のトピックを参照してください。

 

Imports System
Imports System.Threading
Imports System.Reflection
Imports System.Reflection.Emit

 _

Class DynamicJumpTableDemo
   
   Public Shared Function BuildMyType() As Type

      Dim myDomain As AppDomain = Thread.GetDomain()
      Dim myAsmName As New AssemblyName()
      myAsmName.Name = "MyDynamicAssembly"
      
      Dim myAsmBuilder As AssemblyBuilder = myDomain.DefineDynamicAssembly(myAsmName, _
                            AssemblyBuilderAccess.Run)
      Dim myModBuilder As ModuleBuilder = myAsmBuilder.DefineDynamicModule("MyJumpTableDemo")
      
      Dim myTypeBuilder As TypeBuilder = myModBuilder.DefineType("JumpTableDemo", _
                                 TypeAttributes.Public)
      Dim myMthdBuilder As MethodBuilder = myTypeBuilder.DefineMethod("SwitchMe", _
                        MethodAttributes.Public Or MethodAttributes.Static, _
                        GetType(String), New Type() {GetType(Integer)})
      
      Dim myIL As ILGenerator = myMthdBuilder.GetILGenerator()
      
      Dim defaultCase As Label = myIL.DefineLabel()
      Dim endOfMethod As Label = myIL.DefineLabel()
      
      ' We are initializing our jump table. Note that the labels
      ' will be placed later using the MarkLabel method. 

      Dim jumpTable() As Label = {myIL.DefineLabel(), _
                  myIL.DefineLabel(), _
                  myIL.DefineLabel(), _
                  myIL.DefineLabel(), _
                  myIL.DefineLabel()}
      
      ' arg0, the number we passed, is pushed onto the stack.
      ' In this case, due to the design of the code sample,
      ' the value pushed onto the stack happens to match the
      ' index of the label (in IL terms, the index of the offset
      ' in the jump table). If this is not the case, such as
      ' when switching based on non-integer values, rules for the correspondence
      ' between the possible case values and each index of the offsets
      ' must be established outside of the ILGenerator.Emit calls,
      ' much as a compiler would.

      myIL.Emit(OpCodes.Ldarg_0)
      myIL.Emit(OpCodes.Switch, jumpTable)
      
      ' Branch on default case
      myIL.Emit(OpCodes.Br_S, defaultCase)
      
      ' Case arg0 = 0
      myIL.MarkLabel(jumpTable(0))
      myIL.Emit(OpCodes.Ldstr, "are no bananas")
      myIL.Emit(OpCodes.Br_S, endOfMethod)
      
      ' Case arg0 = 1
      myIL.MarkLabel(jumpTable(1))
      myIL.Emit(OpCodes.Ldstr, "is one banana")
      myIL.Emit(OpCodes.Br_S, endOfMethod)
      
      ' Case arg0 = 2
      myIL.MarkLabel(jumpTable(2))
      myIL.Emit(OpCodes.Ldstr, "are two bananas")
      myIL.Emit(OpCodes.Br_S, endOfMethod)
      
      ' Case arg0 = 3
      myIL.MarkLabel(jumpTable(3))
      myIL.Emit(OpCodes.Ldstr, "are three bananas")
      myIL.Emit(OpCodes.Br_S, endOfMethod)
      
      ' Case arg0 = 4
      myIL.MarkLabel(jumpTable(4))
      myIL.Emit(OpCodes.Ldstr, "are four bananas")
      myIL.Emit(OpCodes.Br_S, endOfMethod)
      
      ' Default case
      myIL.MarkLabel(defaultCase)
      myIL.Emit(OpCodes.Ldstr, "are many bananas")
      
      myIL.MarkLabel(endOfMethod)
      myIL.Emit(OpCodes.Ret)
      
      Return myTypeBuilder.CreateType()

   End Function 'BuildMyType
    
   
   Public Shared Sub Main()

      Dim myType As Type = BuildMyType()
      
      Console.Write("Enter an integer between 0 and 5: ")
      Dim theValue As Integer = Convert.ToInt32(Console.ReadLine())
      
      Console.WriteLine("---")
      Dim myInstance As [Object] = Activator.CreateInstance(myType, New Object() {})
      Console.WriteLine("Yes, there {0} today!", myType.InvokeMember("SwitchMe", _
                         BindingFlags.InvokeMethod, Nothing, _
                             myInstance, New Object() {theValue}))

   End Sub 'Main

End Class 'DynamicJumpTableDemo


[C#] 

using System;
using System.Threading;
using System.Reflection;
using System.Reflection.Emit;

class DynamicJumpTableDemo

{

   public static Type BuildMyType()
   {
    AppDomain myDomain = Thread.GetDomain();
    AssemblyName myAsmName = new AssemblyName();
    myAsmName.Name = "MyDynamicAssembly";

    AssemblyBuilder myAsmBuilder = myDomain.DefineDynamicAssembly(
                        myAsmName,
                        AssemblyBuilderAccess.Run);
    ModuleBuilder myModBuilder = myAsmBuilder.DefineDynamicModule(
                        "MyJumpTableDemo");

    TypeBuilder myTypeBuilder = myModBuilder.DefineType("JumpTableDemo",
                            TypeAttributes.Public);
    MethodBuilder myMthdBuilder = myTypeBuilder.DefineMethod("SwitchMe", 
                             MethodAttributes.Public |
                             MethodAttributes.Static,
                                             typeof(string), 
                                             new Type[] {typeof(int)});

    ILGenerator myIL = myMthdBuilder.GetILGenerator();

    Label defaultCase = myIL.DefineLabel();    
    Label endOfMethod = myIL.DefineLabel();    

    // We are initializing our jump table. Note that the labels
    // will be placed later using the MarkLabel method. 

    Label[] jumpTable = new Label[] { myIL.DefineLabel(),
                      myIL.DefineLabel(),
                      myIL.DefineLabel(),
                      myIL.DefineLabel(),
                      myIL.DefineLabel() };

    // arg0, the number we passed, is pushed onto the stack.
    // In this case, due to the design of the code sample,
    // the value pushed onto the stack happens to match the
    // index of the label (in IL terms, the index of the offset
    // in the jump table). If this is not the case, such as
    // when switching based on non-integer values, rules for the correspondence
    // between the possible case values and each index of the offsets
    // must be established outside of the ILGenerator.Emit calls,
    // much as a compiler would.

    myIL.Emit(OpCodes.Ldarg_0);
    myIL.Emit(OpCodes.Switch, jumpTable);
    
    // Branch on default case
    myIL.Emit(OpCodes.Br_S, defaultCase);

    // Case arg0 = 0
    myIL.MarkLabel(jumpTable[0]); 
    myIL.Emit(OpCodes.Ldstr, "are no bananas");
    myIL.Emit(OpCodes.Br_S, endOfMethod);

    // Case arg0 = 1
    myIL.MarkLabel(jumpTable[1]); 
    myIL.Emit(OpCodes.Ldstr, "is one banana");
    myIL.Emit(OpCodes.Br_S, endOfMethod);

    // Case arg0 = 2
    myIL.MarkLabel(jumpTable[2]); 
    myIL.Emit(OpCodes.Ldstr, "are two bananas");
    myIL.Emit(OpCodes.Br_S, endOfMethod);

    // Case arg0 = 3
    myIL.MarkLabel(jumpTable[3]); 
    myIL.Emit(OpCodes.Ldstr, "are three bananas");
    myIL.Emit(OpCodes.Br_S, endOfMethod);

    // Case arg0 = 4
    myIL.MarkLabel(jumpTable[4]); 
    myIL.Emit(OpCodes.Ldstr, "are four bananas");
    myIL.Emit(OpCodes.Br_S, endOfMethod);

    // Default case
    myIL.MarkLabel(defaultCase);
    myIL.Emit(OpCodes.Ldstr, "are many bananas");

    myIL.MarkLabel(endOfMethod);
    myIL.Emit(OpCodes.Ret);
    
    return myTypeBuilder.CreateType();

   }

   public static void Main()
   {
    Type myType = BuildMyType();
    
    Console.Write("Enter an integer between 0 and 5: ");
    int theValue = Convert.ToInt32(Console.ReadLine());

    Console.WriteLine("---");
    Object myInstance = Activator.CreateInstance(myType, new object[0]);    
    Console.WriteLine("Yes, there {0} today!", myType.InvokeMember("SwitchMe",
                                 BindingFlags.InvokeMethod,
                                 null,
                                 myInstance,
                                 new object[] {theValue}));  
              
   }

}


[C++] 

#using <mscorlib.dll>

using namespace System;
using namespace System::Threading;
using namespace System::Reflection;
using namespace System::Reflection::Emit;

Type* BuildMyType() {
   AppDomain*  myDomain = Thread::GetDomain();
   AssemblyName* myAsmName = new AssemblyName();
   myAsmName->Name = S"MyDynamicAssembly";

   AssemblyBuilder*  myAsmBuilder = myDomain->DefineDynamicAssembly(myAsmName,
      AssemblyBuilderAccess::Run);
   ModuleBuilder*  myModBuilder = myAsmBuilder->DefineDynamicModule(S"MyJumpTableDemo");

   TypeBuilder*  myTypeBuilder = myModBuilder->DefineType(S"JumpTableDemo",
      TypeAttributes::Public);

   Type* temp0 [] = {__typeof(int)};
   MethodBuilder*  myMthdBuilder = myTypeBuilder->DefineMethod(
      S"SwitchMe",
      static_cast<MethodAttributes>(MethodAttributes::Public | MethodAttributes::Static),
      __typeof(String),
      temp0);

   ILGenerator*  myIL = myMthdBuilder->GetILGenerator();

   Label defaultCase = myIL->DefineLabel();
   Label endOfMethod = myIL->DefineLabel();

   // We are initializing our jump table. Note that the labels
   // will be placed later using the MarkLabel method.

   Label jumpTable [] = new Label[5];
   jumpTable[0] = myIL->DefineLabel();
   jumpTable[1] = myIL->DefineLabel();
   jumpTable[2] = myIL->DefineLabel();
   jumpTable[3] = myIL->DefineLabel();
   jumpTable[4] = myIL->DefineLabel();

   // arg0, the number we passed, is pushed onto the stack.
   // In this case, due to the design of the code sample,
   // the value pushed onto the stack happens to match the
   // index of the label (in IL terms, the index of the offset
   // in the jump table). If this is not the case, such as
   // when switching based on non-integer values, rules for the correspondence
   // between the possible case values and each index of the offsets
   // must be established outside of the ILGenerator::Emit calls,
   // much as a compiler would.

   myIL->Emit(OpCodes::Ldarg_0);
   myIL->Emit(OpCodes::Switch, jumpTable);

   // Branch on default case
   myIL->Emit(OpCodes::Br_S, defaultCase);

   // Case arg0 = 0
   myIL->MarkLabel(jumpTable[0]);
   myIL->Emit(OpCodes::Ldstr, S"are no bananas");
   myIL->Emit(OpCodes::Br_S, endOfMethod);

   // Case arg0 = 1
   myIL->MarkLabel(jumpTable[1]);
   myIL->Emit(OpCodes::Ldstr, S"is one banana");
   myIL->Emit(OpCodes::Br_S, endOfMethod);

   // Case arg0 = 2
   myIL->MarkLabel(jumpTable[2]);
   myIL->Emit(OpCodes::Ldstr, S"are two bananas");
   myIL->Emit(OpCodes::Br_S, endOfMethod);

   // Case arg0 = 3
   myIL->MarkLabel(jumpTable[3]);
   myIL->Emit(OpCodes::Ldstr, S"are three bananas");
   myIL->Emit(OpCodes::Br_S, endOfMethod);

   // Case arg0 = 4
   myIL->MarkLabel(jumpTable[4]);
   myIL->Emit(OpCodes::Ldstr, S"are four bananas");
   myIL->Emit(OpCodes::Br_S, endOfMethod);

   // Default case
   myIL->MarkLabel(defaultCase);
   myIL->Emit(OpCodes::Ldstr, S"are many bananas");

   myIL->MarkLabel(endOfMethod);
   myIL->Emit(OpCodes::Ret);

   return myTypeBuilder->CreateType();
}

int main() {
   Type*  myType = BuildMyType();

   Console::Write(S"Enter an integer between 0 and 5: ");
   int theValue = Convert::ToInt32(Console::ReadLine());

   Console::WriteLine(S"---");
   Object*  myInstance = Activator::CreateInstance(myType, new Object*[0]);

   Object* temp1 [] = {__box(theValue)};
   Console::WriteLine(S"Yes, there {0} today!", myType->InvokeMember(S"SwitchMe",
      BindingFlags::InvokeMethod,
      0,
      myInstance,
      temp1));
}

[JScript] JScript のサンプルはありません。Visual Basic、C#、および C++ のサンプルを表示するには、このページの左上隅にある言語のフィルタ ボタン 言語のフィルタ をクリックします。

参照

ILGenerator クラス | ILGenerator メンバ | System.Reflection.Emit 名前空間