MethodBuilder 類別
定義
重要
部分資訊涉及發行前產品,在發行之前可能會有大幅修改。 Microsoft 對此處提供的資訊,不做任何明確或隱含的瑕疵擔保。
定義並表示動態類別上的方法(或建構子)。
public ref class MethodBuilder abstract : System::Reflection::MethodInfo
public ref class MethodBuilder sealed : System::Reflection::MethodInfo
public ref class MethodBuilder sealed : System::Reflection::MethodInfo, System::Runtime::InteropServices::_MethodBuilder
public abstract class MethodBuilder : System.Reflection.MethodInfo
public sealed class MethodBuilder : System.Reflection.MethodInfo
[System.Runtime.InteropServices.ClassInterface(System.Runtime.InteropServices.ClassInterfaceType.None)]
public sealed class MethodBuilder : System.Reflection.MethodInfo, System.Runtime.InteropServices._MethodBuilder
[System.Runtime.InteropServices.ClassInterface(System.Runtime.InteropServices.ClassInterfaceType.None)]
[System.Runtime.InteropServices.ComVisible(true)]
public sealed class MethodBuilder : System.Reflection.MethodInfo, System.Runtime.InteropServices._MethodBuilder
type MethodBuilder = class
inherit MethodInfo
[<System.Runtime.InteropServices.ClassInterface(System.Runtime.InteropServices.ClassInterfaceType.None)>]
type MethodBuilder = class
inherit MethodInfo
interface _MethodBuilder
[<System.Runtime.InteropServices.ClassInterface(System.Runtime.InteropServices.ClassInterfaceType.None)>]
[<System.Runtime.InteropServices.ComVisible(true)>]
type MethodBuilder = class
inherit MethodInfo
interface _MethodBuilder
Public MustInherit Class MethodBuilder
Inherits MethodInfo
Public NotInheritable Class MethodBuilder
Inherits MethodInfo
Public NotInheritable Class MethodBuilder
Inherits MethodInfo
Implements _MethodBuilder
- 繼承
- 屬性
- 實作
範例
以下範例使用該 MethodBuilder 類別在動態型別中建立方法。
using System;
using System.Reflection;
using System.Reflection.Emit;
class DemoMethodBuilder
{
public static void AddMethodDynamically (TypeBuilder myTypeBld,
string mthdName,
Type[] mthdParams,
Type returnType,
string mthdAction)
{
MethodBuilder myMthdBld = myTypeBld.DefineMethod(
mthdName,
MethodAttributes.Public |
MethodAttributes.Static,
returnType,
mthdParams);
ILGenerator ILout = myMthdBld.GetILGenerator();
int numParams = mthdParams.Length;
for (byte x=0; x < numParams; x++)
{
ILout.Emit(OpCodes.Ldarg_S, x);
}
if (numParams > 1)
{
for (int y=0; y<(numParams-1); y++)
{
switch (mthdAction)
{
case "A": ILout.Emit(OpCodes.Add);
break;
case "M": ILout.Emit(OpCodes.Mul);
break;
default: ILout.Emit(OpCodes.Add);
break;
}
}
}
ILout.Emit(OpCodes.Ret);
}
public static void Main()
{
AppDomain myDomain = AppDomain.CurrentDomain;
AssemblyName asmName = new AssemblyName();
asmName.Name = "MyDynamicAsm";
AssemblyBuilder myAsmBuilder = myDomain.DefineDynamicAssembly(
asmName,
AssemblyBuilderAccess.RunAndSave);
ModuleBuilder myModule = myAsmBuilder.DefineDynamicModule("MyDynamicAsm",
"MyDynamicAsm.dll");
TypeBuilder myTypeBld = myModule.DefineType("MyDynamicType",
TypeAttributes.Public);
// Get info from the user to build the method dynamically.
Console.WriteLine("Let's build a simple method dynamically!");
Console.WriteLine("Please enter a few numbers, separated by spaces.");
string inputNums = Console.ReadLine();
Console.Write("Do you want to [A]dd (default) or [M]ultiply these numbers? ");
string myMthdAction = Console.ReadLine().ToUpper();
Console.Write("Lastly, what do you want to name your new dynamic method? ");
string myMthdName = Console.ReadLine();
// Process inputNums into an array and create a corresponding Type array
int index = 0;
string[] inputNumsList = inputNums.Split();
Type[] myMthdParams = new Type[inputNumsList.Length];
object[] inputValsList = new object[inputNumsList.Length];
foreach (string inputNum in inputNumsList)
{
inputValsList[index] = (object)Convert.ToInt32(inputNum);
myMthdParams[index] = typeof(int);
index++;
}
// Now, call the method building method with the parameters, passing the
// TypeBuilder by reference.
AddMethodDynamically(myTypeBld,
myMthdName,
myMthdParams,
typeof(int),
myMthdAction);
Type myType = myTypeBld.CreateType();
Console.WriteLine("---");
Console.WriteLine("The result of {0} the inputted values is: {1}",
((myMthdAction == "M") ? "multiplying" : "adding"),
myType.InvokeMember(myMthdName,
BindingFlags.InvokeMethod | BindingFlags.Public |
BindingFlags.Static,
null,
null,
inputValsList));
Console.WriteLine("---");
// Let's take a look at the method we created.
// If you are interested in seeing the MSIL generated dynamically for the method
// your program generated, change to the directory where you ran the compiled
// code sample and type "ildasm MyDynamicAsm.dll" at the prompt. When the list
// of manifest contents appears, click on "MyDynamicType" and then on the name of
// of the method you provided during execution.
myAsmBuilder.Save("MyDynamicAsm.dll");
MethodInfo myMthdInfo = myType.GetMethod(myMthdName);
Console.WriteLine("Your Dynamic Method: {0};", myMthdInfo.ToString());
}
}
Imports System.Reflection
Imports System.Reflection.Emit
Class DemoMethodBuilder
Public Shared Sub AddMethodDynamically(ByVal myTypeBld As TypeBuilder, _
ByVal mthdName As String, _
ByVal mthdParams() As Type, _
ByVal returnType As Type, _
ByVal mthdAction As String)
Dim myMthdBld As MethodBuilder = myTypeBld.DefineMethod(mthdName, _
MethodAttributes.Public Or MethodAttributes.Static, _
returnType, _
mthdParams)
Dim ILout As ILGenerator = myMthdBld.GetILGenerator()
Dim numParams As Integer = mthdParams.Length
Dim x As Byte
For x = 0 To numParams - 1
ILout.Emit(OpCodes.Ldarg_S, x)
Next x
If numParams > 1 Then
Dim y As Integer
For y = 0 To (numParams - 1) - 1
Select Case mthdAction
Case "A"
ILout.Emit(OpCodes.Add)
Case "M"
ILout.Emit(OpCodes.Mul)
Case Else
ILout.Emit(OpCodes.Add)
End Select
Next y
End If
ILout.Emit(OpCodes.Ret)
End Sub
Public Shared Sub Main()
Dim myDomain As AppDomain = AppDomain.CurrentDomain
Dim asmName As New AssemblyName()
asmName.Name = "MyDynamicAsm"
Dim myAsmBuilder As AssemblyBuilder = myDomain.DefineDynamicAssembly(asmName, _
AssemblyBuilderAccess.RunAndSave)
Dim myModule As ModuleBuilder = myAsmBuilder.DefineDynamicModule("MyDynamicAsm", _
"MyDynamicAsm.dll")
Dim myTypeBld As TypeBuilder = myModule.DefineType("MyDynamicType", TypeAttributes.Public)
' Get info from the user to build the method dynamically.
Console.WriteLine("Let's build a simple method dynamically!")
Console.WriteLine("Please enter a few numbers, separated by spaces.")
Dim inputNums As String = Console.ReadLine()
Console.Write("Do you want to [A]dd (default) or [M]ultiply these numbers? ")
Dim myMthdAction As String = Console.ReadLine().ToUpper()
Console.Write("Lastly, what do you want to name your new dynamic method? ")
Dim myMthdName As String = Console.ReadLine()
' Process inputNums into an array and create a corresponding Type array
Dim index As Integer = 0
Dim inputNumsList As String() = inputNums.Split()
Dim myMthdParams(inputNumsList.Length - 1) As Type
Dim inputValsList(inputNumsList.Length - 1) As Object
Dim inputNum As String
For Each inputNum In inputNumsList
inputValsList(index) = CType(Convert.ToInt32(inputNum), Object)
myMthdParams(index) = GetType(Integer)
index += 1
Next inputNum
' Now, call the method building method with the parameters, passing the
' TypeBuilder by reference.
AddMethodDynamically(myTypeBld, myMthdName, myMthdParams, GetType(Integer), myMthdAction)
Dim myType As Type = myTypeBld.CreateType()
Dim description as String
If myMthdAction = "M" Then
description = "multiplying"
Else
description = "adding"
End If
Console.WriteLine("---")
Console.WriteLine("The result of {0} the values is: {1}", _
description, _
myType.InvokeMember(myMthdName, _
BindingFlags.InvokeMethod _
Or BindingFlags.Public _
Or BindingFlags.Static, _
Nothing, _
Nothing, _
inputValsList))
Console.WriteLine("---")
' If you are interested in seeing the MSIL generated dynamically for the method
' your program generated, change to the directory where you ran the compiled
' code sample and type "ildasm MyDynamicAsm.dll" at the prompt. When the list
' of manifest contents appears, click on "MyDynamicType" and then on the name of
' of the method you provided during execution.
myAsmBuilder.Save("MyDynamicAsm.dll")
Dim myMthdInfo As MethodInfo = myType.GetMethod(myMthdName)
Console.WriteLine("Your Dynamic Method: {0};", myMthdInfo.ToString())
End Sub
End Class
備註
類別 MethodBuilder 可用來完整描述通用中繼語言 (CIL) 中的方法,包括名稱、屬性、簽章和方法主體。 它會配合 TypeBuilder 類別使用,以在運行時生成類別。
您可以使用反射發射來定義全域方法,並將方法定義為類型成員。 定義方法的 API 會傳回 MethodBuilder 物件。
全域方法
全域方法是使用 ModuleBuilder.DefineGlobalMethod 傳回 MethodBuilder 物件的 方法所定義。
全域方法必須是靜態的。 如果動態模組包含全域方法, ModuleBuilder.CreateGlobalFunctions 則必須先呼叫 方法,才能保存動態模組或包含動態元件,因為 Common Language Runtime 會延後修正動態模組,直到定義所有全域函式為止。
全域原生方法是使用 ModuleBuilder.DefinePInvokeMethod 方法來定義。 平台調用 (PInvoke) 方法不得宣告為抽象或虛擬。 運行時間會設定 MethodAttributes.PinvokeImpl 平台調用方法的屬性。
做為型別成員的方法
使用 TypeBuilder.DefineMethod 方法來定義為類型成員,並傳回 MethodBuilder 物件。
方法 DefineParameter 可用來設定參數的名稱和參數屬性,或傳回值的名稱和參數屬性。 ParameterBuilder這個方法傳回的物件代表參數或傳回值。 ParameterBuilder對象可用來設定封送處理、設定常數值,以及套用自定義屬性。
屬性
列舉成員 MethodAttributes 會定義動態方法的精確特性:
- 靜態方法是使用 MethodAttributes.Static 屬性來指定。
- 最後的方法(無法覆寫的方法)是使用 MethodAttributes.Final 屬性來指定。
- 虛擬方法是使用 MethodAttributes.Virtual 屬性來指定。
- 抽象方法是使用 MethodAttributes.Abstract 屬性來指定。
- 數個屬性會決定方法可見性。 請參閱 MethodAttributes 列舉項的描述。
- 實作多載運算子的方法必須設定 MethodAttributes.SpecialName 屬性。
- 完成項必須設定 MethodAttributes.SpecialName 屬性。
已知的問題
- 雖然 MethodBuilder 衍生自 MethodInfo,但 類別中 MethodInfo 定義的一些抽象方法並未在 中 MethodBuilder完全實作。 這些 MethodBuilder 方法會擲回 NotSupportedException。 例如, MethodBuilder.Invoke 方法並未完全實作。 您可以使用 Type.GetType 或 Assembly.GetType 方法來擷取封入型別,以反映這些方法。
- 支援自定義修飾詞。
建構函式
| 名稱 | Description |
|---|---|
| MethodBuilder() |
初始化 MethodBuilder 類別的新執行個體。 |
屬性
| 名稱 | Description |
|---|---|
| Attributes |
取得此方法的屬性。 |
| CallingConvention |
回傳方法的呼叫慣例。 |
| ContainsGenericParameters |
此類型不支援。 |
| CustomAttributes |
會獲得包含該成員自訂屬性的集合。 (繼承來源 MemberInfo) |
| DeclaringType |
回傳宣告此方法的型別。 |
| InitLocals |
取得或設定一個布林值,指定此方法中的局部變數是否為零初始化。 此屬性的預設值為 |
| InitLocalsCore |
當在導出類別中覆寫時,會獲得或設定一個值,指示此方法中的局部變數是否為零初始化。 |
| IsAbstract |
會得到一個值,表示該方法是否為抽象。 (繼承來源 MethodBase) |
| IsAssembly |
獲得一個值,表示此方法或建構子的潛在可見性是否由 Assembly描述;也就是說,該方法或建構器最多對同一組裝中的其他型別可見,對組裝外的衍生型別則無法看到。 (繼承來源 MethodBase) |
| IsCollectible |
獲得一個值,表示該 MemberInfo 物件是否參考收藏品 AssemblyLoadContext中一個或多個組件。 (繼承來源 MemberInfo) |
| IsConstructedGenericMethod |
定義並表示動態類別上的方法(或建構子)。 |
| IsConstructedGenericMethod |
定義並表示動態類別上的方法(或建構子)。 (繼承來源 MethodBase) |
| IsConstructor |
會得到一個值,表示該方法是否為建構子。 (繼承來源 MethodBase) |
| IsFamily |
獲得一個值,表示此方法或建構子的可見性是否由 Family描述;也就是說,該方法或建構子僅在其類別及其衍生類別中可見。 (繼承來源 MethodBase) |
| IsFamilyAndAssembly |
會得到一個值,表示此方法或建構子的可見性是否由 FamANDAssem描述;也就是說,該方法或建構子可以被導出類別呼叫,但前提是它們位於同一組建構中。 (繼承來源 MethodBase) |
| IsFamilyOrAssembly |
會得到一個值,表示此方法或建構子的潛在可見性是否由 FamORAssem描述;也就是說,該方法或建構子可以被派生類別呼叫,無論它們所在的位置,或同一組合語言中的類別。 (繼承來源 MethodBase) |
| IsFinal |
得到一個值,表示此方法是否為 |
| IsGenericMethod |
會得到一個值,表示該方法是否為通用方法。 |
| IsGenericMethodDefinition |
會得到一個值,表示目前 MethodBuilder 物件是否代表一般方法的定義。 |
| IsHideBySig |
會得到一個值,表示導出類別中是否只有同類型且簽名完全相同的成員被隱藏。 (繼承來源 MethodBase) |
| IsPrivate |
會獲得一個值,表示該成員是否為私人。 (繼承來源 MethodBase) |
| IsPublic |
會有一個值來表示這是否是一個公開方法。 (繼承來源 MethodBase) |
| IsSecurityCritical |
在所有情況下都投擲 a NotSupportedException 。 |
| IsSecurityCritical |
會獲得一個值,表示目前的方法或建構子在當前信任層級下是安全關鍵還是安全關鍵,因此可以執行關鍵操作。 (繼承來源 MethodBase) |
| IsSecuritySafeCritical |
在所有情況下都投擲 a NotSupportedException 。 |
| IsSecuritySafeCritical |
獲得一個值,表示目前的方法或建構子在當前信任層級是否為安全關鍵;也就是說,它是否能執行關鍵操作,且是否能被透明程式碼存取。 (繼承來源 MethodBase) |
| IsSecurityTransparent |
在所有情況下都投擲 a NotSupportedException 。 |
| IsSecurityTransparent |
會獲得一個值,表示目前的方法或建構子在目前信任層級是否透明,因此無法執行關鍵操作。 (繼承來源 MethodBase) |
| IsSpecialName |
會得到一個值,表示此方法是否有特殊名稱。 (繼承來源 MethodBase) |
| IsStatic |
獲得一個值,表示該方法是否為 |
| IsVirtual |
獲得一個值,表示該方法是否為 |
| MemberType |
會得到 MemberTypes 一個值,表示該成員是一個方法。 (繼承來源 MethodInfo) |
| MetadataToken |
會取得一個標記,用來識別當前動態模組的元資料。 |
| MetadataToken |
會得到一個識別元資料元素的值。 (繼承來源 MemberInfo) |
| MethodHandle |
取得方法的內部 handle。 使用此代言人來存取底層的元資料代言人。 |
| MethodImplementationFlags |
定義並表示動態類別上的方法(或建構子)。 |
| MethodImplementationFlags |
取得 MethodImplAttributes 指定方法實作屬性的旗標。 (繼承來源 MethodBase) |
| Module |
取得目前方法所定義的模組。 |
| Module |
取得定義宣告電流所代表 MemberInfo 成員型態的模組。 (繼承來源 MemberInfo) |
| Name |
取得此方法名稱。 |
| ReflectedType |
擷取在反射中用來取得此物件的類別。 |
| ReturnParameter |
取得 ParameterInfo 一個包含方法回傳類型資訊的物件,例如該回傳類型是否有自訂修飾符。 |
| ReturnType |
取得由 MethodBuilder所表示的方法的回傳類型。 |
| ReturnType |
取得此方法的回傳類型。 (繼承來源 MethodInfo) |
| ReturnTypeCustomAttributes |
回傳方法回傳類型中的自訂屬性。 |
| ReturnTypeCustomAttributes |
取得返回型態的自訂屬性。 (繼承來源 MethodInfo) |
| Signature |
取得方法的簽名。 |