Delegate.CreateDelegate 方法

定义

创建指定类型的委托。

重载

名称 说明
CreateDelegate(Type, Object, String, Boolean, Boolean)

创建一个指定类型的委托,该委托表示在指定类实例上调用的指定实例方法,该委托具有指定的区分大小写,以及无法绑定的指定行为。

CreateDelegate(Type, Type, String, Boolean)

创建一个指定类型的委托,该委托表示指定类的指定静态方法,具有指定的区分大小写。

CreateDelegate(Type, Object, String, Boolean)

创建指定类型的委托,该委托表示在具有指定大小写的指定类实例上调用的指定实例方法。

CreateDelegate(Type, Object, MethodInfo, Boolean)

创建一个代表指定静态或实例方法的指定类型的委托,该委托具有指定的第一个参数和无法绑定的指定行为。

CreateDelegate(Type, Type, String, Boolean, Boolean)

创建一个指定类型的委托,该委托表示指定类的指定静态方法,指定区分大小写,以及无法绑定的指定行为。

CreateDelegate(Type, MethodInfo, Boolean)

创建指定类型的委托来表示指定的静态方法,并指定了绑定失败时的行为。

CreateDelegate(Type, Object, String)

创建表示在指定类实例上调用的指定实例方法的指定类型的委托。

CreateDelegate(Type, Object, MethodInfo)

使用指定的第一个参数创建表示指定静态或实例方法的指定类型的委托。

CreateDelegate(Type, MethodInfo)

创建指定类型的委托来表示指定的方法。

CreateDelegate(Type, Type, String)

创建表示指定类的指定静态方法的指定类型的委托。

CreateDelegate(Type, Object, String, Boolean, Boolean)

Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs

创建一个指定类型的委托,该委托表示在指定类实例上调用的指定实例方法,该委托具有指定的区分大小写,以及无法绑定的指定行为。

public:
 static Delegate ^ CreateDelegate(Type ^ type, System::Object ^ target, System::String ^ method, bool ignoreCase, bool throwOnBindFailure);
[System.Diagnostics.CodeAnalysis.RequiresUnreferencedCode("The target method might be removed")]
public static Delegate? CreateDelegate(Type type, object target, string method, bool ignoreCase, bool throwOnBindFailure);
public static Delegate CreateDelegate(Type type, object target, string method, bool ignoreCase, bool throwOnBindFailure);
public static Delegate? CreateDelegate(Type type, object target, string method, bool ignoreCase, bool throwOnBindFailure);
[<System.Diagnostics.CodeAnalysis.RequiresUnreferencedCode("The target method might be removed")>]
static member CreateDelegate : Type * obj * string * bool * bool -> Delegate
static member CreateDelegate : Type * obj * string * bool * bool -> Delegate
Public Shared Function CreateDelegate (type As Type, target As Object, method As String, ignoreCase As Boolean, throwOnBindFailure As Boolean) As Delegate

参数

type
Type

Type要创建的委托。

target
Object

对其调用的 method 类实例。

method
String

委托要表示的实例方法的名称。

ignoreCase
Boolean

一个布尔值,指示在比较方法名称时是否忽略大小写。

throwOnBindFailure
Boolean

如果 无法绑定,则为 ;否则为 >。

返回

指定类型的委托,表示在指定类实例上调用的指定实例方法。

属性

例外

typenull

-或-

targetnull

-或-

methodnull

type 不继承 MulticastDelegate

-或-

type不是 .RuntimeType 请参阅 反射中的运行时类型

-或-

method 不是实例方法。

-或-

method 无法绑定,例如,因为它找不到,并且 throwOnBindFailuretrue

Invoke找不到方法type

调用方没有访问 method所需的权限。

注解

此方法仅为实例方法创建委托。 实例方法是与类实例关联的方法;静态方法是与类本身关联的方法。

另请参阅

适用于

CreateDelegate(Type, Type, String, Boolean)

Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs

创建一个指定类型的委托,该委托表示指定类的指定静态方法,具有指定的区分大小写。

public:
 static Delegate ^ CreateDelegate(Type ^ type, Type ^ target, System::String ^ method, bool ignoreCase);
public static Delegate CreateDelegate(Type type, Type target, string method, bool ignoreCase);
[System.Diagnostics.CodeAnalysis.RequiresUnreferencedCode("The target method might be removed")]
public static Delegate CreateDelegate(Type type, Type target, string method, bool ignoreCase);
static member CreateDelegate : Type * Type * string * bool -> Delegate
[<System.Diagnostics.CodeAnalysis.RequiresUnreferencedCode("The target method might be removed")>]
static member CreateDelegate : Type * Type * string * bool -> Delegate
Public Shared Function CreateDelegate (type As Type, target As Type, method As String, ignoreCase As Boolean) As Delegate

参数

type
Type

Type要创建的委托。

target
Type

Type表示实现method的类。

method
String

委托要表示的静态方法的名称。

ignoreCase
Boolean

一个布尔值,指示在比较方法名称时是否忽略大小写。

返回

表示指定类的指定静态方法的委托。

属性

例外

typenull

-或-

targetnull

-或-

methodnull

type 不继承 MulticastDelegate

-或-

type不是 .RuntimeType 请参阅 反射中的运行时类型

-或-

target不是 .RuntimeType

-或-

target 是一种打开的泛型类型。 也就是说,其 ContainsGenericParameters 属性为 true.

-或-

method 不是 static 方法(Visual Basic中的 Shared 方法)。

-或-

method 无法绑定,例如,因为它找不到。

Invoke找不到方法type

调用方没有访问 method所需的权限。

注解

此方法仅为静态方法创建委托。 实例方法是与类实例关联的方法;静态方法是与类本身关联的方法。

此方法重载等效于调用CreateDelegate(Type, Type, String, Boolean, Boolean)方法重载,并true指定 。throwOnBindFailure

另请参阅

适用于

CreateDelegate(Type, Object, String, Boolean)

Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs

创建指定类型的委托,该委托表示在具有指定大小写的指定类实例上调用的指定实例方法。

public:
 static Delegate ^ CreateDelegate(Type ^ type, System::Object ^ target, System::String ^ method, bool ignoreCase);
[System.Diagnostics.CodeAnalysis.RequiresUnreferencedCode("The target method might be removed")]
public static Delegate CreateDelegate(Type type, object target, string method, bool ignoreCase);
public static Delegate CreateDelegate(Type type, object target, string method, bool ignoreCase);
[<System.Diagnostics.CodeAnalysis.RequiresUnreferencedCode("The target method might be removed")>]
static member CreateDelegate : Type * obj * string * bool -> Delegate
static member CreateDelegate : Type * obj * string * bool -> Delegate
Public Shared Function CreateDelegate (type As Type, target As Object, method As String, ignoreCase As Boolean) As Delegate

参数

type
Type

Type要创建的委托。

target
Object

对其调用的 method 类实例。

method
String

委托要表示的实例方法的名称。

ignoreCase
Boolean

一个布尔值,指示在比较方法名称时是否忽略大小写。

返回

指定类型的委托,表示在指定类实例上调用的指定实例方法。

属性

例外

typenull

-或-

targetnull

-或-

methodnull

type 不继承 MulticastDelegate

-或-

type不是 .RuntimeType 请参阅 反射中的运行时类型

-或-

method 不是实例方法。

-或-

method 无法绑定,例如,因为它找不到。

Invoke找不到方法type

调用方没有访问 method所需的权限。

注解

此方法仅为实例方法创建委托。 实例方法是与类实例关联的方法;静态方法是与类本身关联的方法。

此方法重载等效于调用CreateDelegate(Type, Object, String, Boolean, Boolean)方法重载,并true指定 。throwOnBindFailure

另请参阅

适用于

CreateDelegate(Type, Object, MethodInfo, Boolean)

Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs

创建一个代表指定静态或实例方法的指定类型的委托,该委托具有指定的第一个参数和无法绑定的指定行为。

public:
 static Delegate ^ CreateDelegate(Type ^ type, System::Object ^ firstArgument, System::Reflection::MethodInfo ^ method, bool throwOnBindFailure);
public static Delegate? CreateDelegate(Type type, object? firstArgument, System.Reflection.MethodInfo method, bool throwOnBindFailure);
public static Delegate CreateDelegate(Type type, object firstArgument, System.Reflection.MethodInfo method, bool throwOnBindFailure);
static member CreateDelegate : Type * obj * System.Reflection.MethodInfo * bool -> Delegate
Public Shared Function CreateDelegate (type As Type, firstArgument As Object, method As MethodInfo, throwOnBindFailure As Boolean) As Delegate

参数

type
Type

表示 Type 要创建的委托的类型。

firstArgument
Object

这是委托表示的方法的第一个 Object 参数。 对于实例方法,它必须与实例类型兼容。

method
MethodInfo

MethodInfo描述委托要表示的静态或实例方法。

throwOnBindFailure
Boolean

如果 无法绑定,则为 ;否则为 >。

返回

表示指定静态或实例方法的指定类型的委托,或者 null 如果 throwOnBindFailurefalse 且委托不能绑定到 method

例外

typenull

-或-

methodnull

type 不继承 MulticastDelegate

-或-

type不是 .RuntimeType 请参阅 反射中的运行时类型

-或-

method 不能绑定,并且 throwOnBindFailuretrue

-或-

method不是 .RuntimeMethodInfo 请参阅 反射中的运行时类型

Invoke找不到方法type

调用方没有访问 method所需的权限。

注解

此方法重载和 CreateDelegate(Type, Object, MethodInfo) 方法重载(始终在绑定失败时引发)提供了创建委托的最灵活方法。 可以使用它们为静态方法或实例方法创建委托,以及不带第一个参数。

注释

如果未提供第一个参数,请使用 CreateDelegate(Type, MethodInfo, Boolean) 方法重载来提高性能。

委托类型和方法必须具有兼容的返回类型。 也就是说,method 的返回类型必须可以赋值给 type 的返回类型。

firstArgument,这些重载的第二个参数是委托表示的方法的第一个参数。 如果提供了 firstArgument,那么每次调用委托时它都会被传递给 method;此时可以说 firstArgument 绑定到了该委托,并且称该委托在其第一个参数上形成闭包。 如果 methodstaticShared 在 Visual Basic 中),则调用委托时提供的参数列表包括除第一个参数以外的所有参数;如果是 method 实例方法,则 firstArgument 传递给隐藏实例参数(在 this C# 中或 Me Visual Basic 中表示)。

如果 firstArgument 提供,则第一个参数 method 必须是引用类型,并且 firstArgument 必须与该类型兼容。

Important

如果 methodstaticShared 在 Visual Basic 中)及其第一个参数的类型 ObjectValueTypefirstArgument 可以是值类型。 在这种情况下 firstArgument 会自动装箱。 与在 C# 或 Visual Basic 函数调用中一样,对于任何其他参数都不会发生自动装箱。

如果 firstArgument 是 null 引用,并且 method 是实例方法,则结果取决于委托类型 typemethod 的签名。

  • 如果 type 的签名显式包含 method 的第一个隐藏参数,则称该委托表示一个开放实例方法。 调用委托时,参数列表中的第一个参数将传递给隐藏的 method实例参数。
  • 如果签名 methodtype 匹配(即所有参数类型都兼容),则称该委托在空引用上形成闭包。 调用委托就像对 null 实例调用实例方法一样,这不是一件特别有用的事情。

如果 firstArgument 为 null 引用且 method 是静态的,则结果取决于委托类型 typemethod 的签名。

  • 如果签名 methodtype 匹配(即所有参数类型都兼容),则表示委托表示开放静态方法。 这是静态方法最常见的情况。 在这种情况下,通过使用CreateDelegate(Type, MethodInfo) 方法重载可以获得更好的性能。
  • 如果 type 的签名以 method 的第二个参数开头,并且其余参数类型兼容,则称该委托在空引用上形成闭包。 调用委托时,向第一个参数 method传递空引用。

示例

下面的代码示例演示单个委托类型可以表示的所有方法:在实例方法上关闭、在实例方法上打开、在静态方法上打开,并通过静态方法关闭。

该代码示例定义了两个类CF,以及一个具有D类型参数的委托类型C。 这些类具有匹配的静态和实例方法 M1M3并且 M4C 也具有没有参数的实例方法 M2

名为 Example 的第三个类包含创建委托的代码。

  • 为类型 M1 和类型 C 的实例方法 F 创建委托;每个委托都在各自类型的一个实例上形成闭包。 类型为 M1 的方法 C 显示绑定实例和参数的 ID 属性。
  • 为类型 M2 的方法 C 创建一个委托。 这是一个开放实例委托,其中委托的参数表示实例方法上隐藏的第一个参数。 该方法没有其他参数。 它的调用方式就像是调用一个静态方法。
  • 为类型M3和类型C的静态方法F创建委托;这些是开放的静态委托。
  • 最后,为类型 M4 和类型 C 的静态方法 F 创建委托;每个方法都将声明类型作为其第一个参数,并提供该类型的一个实例,因此这些委托在其第一个参数上形成闭包。 类型为 M4 的方法 C 显示绑定实例和参数的 ID 属性。
using System;
using System.Reflection;

// Declare a delegate type. The object of this code example
// is to show all the methods this delegate can bind to.
//
public delegate void D(C1 c);

// Declare two sample classes, C1 and F. Class C1 has an ID
// property so instances can be identified.
//
public class C1
{
    private int id;
    public int ID => id;
    public C1(int id) => this.id = id;

    public void M1(C1 c)
    {
        Console.WriteLine("Instance method M1(C1 c) on C1:  this.id = {0}, c.ID = {1}",
            this.id, c.ID);
    }

    public void M2()
    {
        Console.WriteLine($"Instance method M2() on C1:  this.id = {this.id}");
    }

    public static void M3(C1 c)
    {
        Console.WriteLine($"Static method M3(C1 c) on C1:  c.ID = {c.ID}");
    }

    public static void M4(C1 c1, C1 c2)
    {
        Console.WriteLine("Static method M4(C1 c1, C1 c2) on C1:  c1.ID = {0}, c2.ID = {1}",
            c1.ID, c2.ID);
    }
}

public class F
{
    public void M1(C1 c)
    {
        Console.WriteLine($"Instance method M1(C1 c) on F:  c.ID = {c.ID}");
    }

    public static void M3(C1 c)
    {
        Console.WriteLine($"Static method M3(C1 c) on F:  c.ID = {c.ID}");
    }

    public static void M4(F f, C1 c)
    {
        Console.WriteLine($"Static method M4(F f, C1 c) on F:  c.ID = {c.ID}");
    }
}

public class Example
{
    public static void Main()
    {
        C1 c1 = new (42);
        C1 c2 = new (1491);
        F f1 = new ();

        D d;

        // Instance method with one argument of type C1.
        MethodInfo cmi1 = typeof(C1).GetMethod("M1");
        // Instance method with no arguments.
        MethodInfo cmi2 = typeof(C1).GetMethod("M2");
        // Static method with one argument of type C1.
        MethodInfo cmi3 = typeof(C1).GetMethod("M3");
        // Static method with two arguments of type C1.
        MethodInfo cmi4 = typeof(C1).GetMethod("M4");

        // Instance method with one argument of type C1.
        MethodInfo fmi1 = typeof(F).GetMethod("M1");
        // Static method with one argument of type C1.
        MethodInfo fmi3 = typeof(F).GetMethod("M3");
        // Static method with an argument of type F and an argument
        // of type C1.
        MethodInfo fmi4 = typeof(F).GetMethod("M4");

        Console.WriteLine("\nAn instance method on any type, with an argument of type C1.");
        // D can represent any instance method that exactly matches its
        // signature. Methods on C1 and F are shown here.
        //
        d = (D)Delegate.CreateDelegate(typeof(D), c1, cmi1);
        d(c2);
        d = (D)Delegate.CreateDelegate(typeof(D), f1, fmi1);
        d(c2);

        Console.WriteLine("\nAn instance method on C1 with no arguments.");
        // D can represent an instance method on C1 that has no arguments;
        // in this case, the argument of D represents the hidden first
        // argument of any instance method. The delegate acts like a
        // static method, and an instance of C1 must be passed each time
        // it is invoked.
        //
        d = (D)Delegate.CreateDelegate(typeof(D), null, cmi2);
        d(c1);

        Console.WriteLine("\nA static method on any type, with an argument of type C1.");
        // D can represent any static method with the same signature.
        // Methods on F and C1 are shown here.
        //
        d = (D)Delegate.CreateDelegate(typeof(D), null, cmi3);
        d(c1);
        d = (D)Delegate.CreateDelegate(typeof(D), null, fmi3);
        d(c1);

        Console.WriteLine("\nA static method on any type, with an argument of");
        Console.WriteLine("    that type and an argument of type C1.");
        // D can represent any static method with one argument of the
        // type the method belongs and a second argument of type C1.
        // In this case, the method is closed over the instance of
        // supplied for the its first argument, and acts like an instance
        // method. Methods on F and C1 are shown here.
        //
        d = (D)Delegate.CreateDelegate(typeof(D), c1, cmi4);
        d(c2);
        Delegate test =
            Delegate.CreateDelegate(typeof(D), f1, fmi4, false);

        // This final example specifies false for throwOnBindFailure
        // in the call to CreateDelegate, so the variable 'test'
        // contains Nothing if the method fails to bind (for
        // example, if fmi4 happened to represent a method of
        // some class other than F).
        //
        if (test != null)
        {
            d = (D)test;
            d(c2);
        }
    }
}

/* This code example produces the following output:

An instance method on any type, with an argument of type C1.
Instance method M1(C1 c) on C1:  this.id = 42, c.ID = 1491
Instance method M1(C1 c) on F:  c.ID = 1491

An instance method on C1 with no arguments.
Instance method M2() on C1:  this.id = 42

A static method on any type, with an argument of type C1.
Static method M3(C1 c) on C1:  c.ID = 42
Static method M3(C1 c) on F:  c.ID = 42

A static method on any type, with an argument of
    that type and an argument of type C1.
Static method M4(C1 c1, C1 c2) on C1:  c1.ID = 42, c2.ID = 1491
Static method M4(F f, C1 c) on F:  c.ID = 1491
*/
open System

// Declare two sample classes, C and F. Class C has an ID
// property so instances can be identified.
type C(id) =
    member _.ID = id 

    member _.M1(c: C) =
        printfn $"Instance method M1(C c) on C:  this.id = {id}, c.ID = {c.ID}"

    member _.M2() =
        printfn $"Instance method M2() on C:  this.id = {id}"

    static member M3(c: C) =
        printfn $"Static method M3(C c) on C:  c.ID = {c.ID}"

    static member M4(c1: C, c2: C) =
        printfn $"Static method M4(C c1, C c2) on C:  c1.ID = {c1.ID}, c2.ID = {c2.ID}"

// Declare a delegate type. The object of this code example
// is to show all the methods this delegate can bind to.
type D = delegate of C -> unit


type F() =
    member _.M1(c: C) =
        printfn $"Instance method M1(C c) on F:  c.ID = {c.ID}"

    member _.M3(c: C) =
        printfn $"Static method M3(C c) on F:  c.ID = {c.ID}"

    member _.M4(f: F, c: C) =
        printfn $"Static method M4(F f, C c) on F:  c.ID = {c.ID}"

[<EntryPoint>]
let main _ =
    let c1 = C 42
    let c2 = C 1491
    let f1 = F()

    // Instance method with one argument of type C.
    let cmi1 = typeof<C>.GetMethod "M1"
    // Instance method with no arguments.
    let cmi2 = typeof<C>.GetMethod "M2"
    // Static method with one argument of type C.
    let cmi3 = typeof<C>.GetMethod "M3"
    // Static method with two arguments of type C.
    let cmi4 = typeof<C>.GetMethod "M4"

    // Instance method with one argument of type C.
    let fmi1 = typeof<F>.GetMethod "M1"
    // Static method with one argument of type C.
    let fmi3 = typeof<F>.GetMethod "M3"
    // Static method with an argument of type F and an argument
    // of type C.
    let fmi4 = typeof<F>.GetMethod "M4"

    printfn "\nAn instance method on any type, with an argument of type C."
    // D can represent any instance method that exactly matches its
    // signature. Methods on C and F are shown here.
    let d = Delegate.CreateDelegate(typeof<D>, c1, cmi1) :?> D
    d.Invoke c2
    let d =  Delegate.CreateDelegate(typeof<D>, f1, fmi1) :?> D
    d.Invoke c2

    Console.WriteLine("\nAn instance method on C with no arguments.")
    // D can represent an instance method on C that has no arguments
    // in this case, the argument of D represents the hidden first
    // argument of any instance method. The delegate acts like a
    // static method, and an instance of C must be passed each time
    // it is invoked.
    let d = Delegate.CreateDelegate(typeof<D>, null, cmi2) :?> D
    d.Invoke c1

    printfn "\nA static method on any type, with an argument of type C."
    // D can represent any static method with the same signature.
    // Methods on F and C are shown here.
    let d = Delegate.CreateDelegate(typeof<D>, null, cmi3) :?> D
    d.Invoke c1
    let d = Delegate.CreateDelegate(typeof<D>, null, fmi3) :?> D
    d.Invoke c1

    printfn "\nA static method on any type, with an argument of"
    printfn "    that type and an argument of type C."
    // D can represent any static method with one argument of the
    // type the method belongs and a second argument of type C.
    // In this case, the method is closed over the instance of
    // supplied for the its first argument, and acts like an instance
    // method. Methods on F and C are shown here.
    let d = Delegate.CreateDelegate(typeof<D>, c1, cmi4) :?> D
    d.Invoke c2
    let test =
        Delegate.CreateDelegate(typeof<D>, f1, fmi4, false)

    // This final example specifies false for throwOnBindFailure
    // in the call to CreateDelegate, so the variable 'test'
    // contains Nothing if the method fails to bind (for
    // example, if fmi4 happened to represent a method of
    // some class other than F).
    match test with
    | :? D as d ->
        d.Invoke c2
    | _ -> ()
    0

// This code example produces the following output:
//     An instance method on any type, with an argument of type C.
//     Instance method M1(C c) on C:  this.id = 42, c.ID = 1491
//     Instance method M1(C c) on F:  c.ID = 1491
//    
//     An instance method on C with no arguments.
//     Instance method M2() on C:  this.id = 42
//    
//     A static method on any type, with an argument of type C.
//     Static method M3(C c) on C:  c.ID = 42
//     Static method M3(C c) on F:  c.ID = 42
//    
//     A static method on any type, with an argument of
//         that type and an argument of type C.
//     Static method M4(C c1, C c2) on C:  c1.ID = 42, c2.ID = 1491
//     Static method M4(F f, C c) on F:  c.ID = 1491
Imports System.Reflection
Imports System.Security.Permissions

' Declare a delegate type. The object of this code example
' is to show all the methods this delegate can bind to.
'
Public Delegate Sub D(ByVal c As C) 

' Declare two sample classes, C and F. Class C has an ID
' property so instances can be identified.
'
Public Class C

    Private _id As Integer

    Public ReadOnly Property ID() As Integer 
        Get
            Return _id
        End Get
    End Property

    Public Sub New(ByVal newId As Integer) 
        Me._id = newId
    End Sub
    
    Public Sub M1(ByVal c As C) 
        Console.WriteLine("Instance method M1(c As C) on C:  this.id = {0}, c.ID = {1}", _
            Me.id, c.ID)
    End Sub
    
    Public Sub M2() 
        Console.WriteLine("Instance method M2() on C:  this.id = {0}", Me.id)
    End Sub
    
    Public Shared Sub M3(ByVal c As C) 
        Console.WriteLine("Shared method M3(c As C) on C:  c.ID = {0}", c.ID)
    End Sub
    
    Public Shared Sub M4(ByVal c1 As C, ByVal c2 As C) 
        Console.WriteLine("Shared method M4(c1 As C, c2 As C) on C:  c1.ID = {0}, c2.ID = {1}", _
            c1.ID, c2.ID)
    End Sub
End Class


Public Class F
    
    Public Sub M1(ByVal c As C) 
        Console.WriteLine("Instance method M1(c As C) on F:  c.ID = {0}", c.ID)
    End Sub
    
    Public Shared Sub M3(ByVal c As C) 
        Console.WriteLine("Shared method M3(c As C) on F:  c.ID = {0}", c.ID)
    End Sub
    
    Public Shared Sub M4(ByVal f As F, ByVal c As C) 
        Console.WriteLine("Shared method M4(f As F, c As C) on F:  c.ID = {0}", c.ID)
    End Sub
End Class

Public Class Example5

    Public Shared Sub Main()

        Dim c1 As New C(42)
        Dim c2 As New C(1491)
        Dim f1 As New F()

        Dim d As D

        ' Instance method with one argument of type C.
        Dim cmi1 As MethodInfo = GetType(C).GetMethod("M1")
        ' Instance method with no arguments.
        Dim cmi2 As MethodInfo = GetType(C).GetMethod("M2")
        ' Shared method with one argument of type C.
        Dim cmi3 As MethodInfo = GetType(C).GetMethod("M3")
        ' Shared method with two arguments of type C.
        Dim cmi4 As MethodInfo = GetType(C).GetMethod("M4")

        ' Instance method with one argument of type C.
        Dim fmi1 As MethodInfo = GetType(F).GetMethod("M1")
        ' Shared method with one argument of type C.
        Dim fmi3 As MethodInfo = GetType(F).GetMethod("M3")
        ' Shared method with an argument of type F and an 
        ' argument of type C.
        Dim fmi4 As MethodInfo = GetType(F).GetMethod("M4")

        Console.WriteLine(vbLf & "An instance method on any type, with an argument of type C.")
        ' D can represent any instance method that exactly matches its
        ' signature. Methods on C and F are shown here.
        '
        d = CType([Delegate].CreateDelegate(GetType(D), c1, cmi1), D)
        d(c2)
        d = CType([Delegate].CreateDelegate(GetType(D), f1, fmi1), D)
        d(c2)

        Console.WriteLine(vbLf & "An instance method on C with no arguments.")
        ' D can represent an instance method on C that has no arguments;
        ' in this case, the argument of D represents the hidden first
        ' argument of any instance method. The delegate acts like a 
        ' Shared method, and an instance of C must be passed each time
        ' it is invoked.
        '
        d = CType([Delegate].CreateDelegate(GetType(D), Nothing, cmi2), D)
        d(c1)

        Console.WriteLine(vbLf & "A Shared method on any type, with an argument of type C.")
        ' D can represent any Shared method with the same signature.
        ' Methods on F and C are shown here.
        '
        d = CType([Delegate].CreateDelegate(GetType(D), Nothing, cmi3), D)
        d(c1)
        d = CType([Delegate].CreateDelegate(GetType(D), Nothing, fmi3), D)
        d(c1)

        Console.WriteLine(vbLf & "A Shared method on any type, with an argument of")
        Console.WriteLine("    that type and an argument of type C.")
        ' D can represent any Shared method with one argument of the
        ' type the method belongs and a second argument of type C.
        ' In this case, the method is closed over the instance of
        ' supplied for the its first argument, and acts like an instance
        ' method. Methods on F and C are shown here.
        '
        d = CType([Delegate].CreateDelegate(GetType(D), c1, cmi4), D)
        d(c2)
        Dim test As [Delegate] =
            [Delegate].CreateDelegate(GetType(D), f1, fmi4, False)

        ' This final example specifies False for throwOnBindFailure 
        ' in the call to CreateDelegate, so the variable 'test'
        ' contains Nothing if the method fails to bind (for 
        ' example, if fmi4 happened to represent a method of  
        ' some class other than F).
        '
        If test IsNot Nothing Then
            d = CType(test, D)
            d(c2)
        End If

    End Sub
End Class

' This code example produces the following output:
'
'An instance method on any type, with an argument of type C.
'Instance method M1(c As C) on C:  this.id = 42, c.ID = 1491
'Instance method M1(c As C) on F:  c.ID = 1491
'
'An instance method on C with no arguments.
'Instance method M2() on C:  this.id = 42
'
'A Shared method on any type, with an argument of type C.
'Shared method M3(c As C) on C:  c.ID = 42
'Shared method M3(c As C) on F:  c.ID = 42
'
'A Shared method on any type, with an argument of
'    that type and an argument of type C.
'Shared method M4(c1 As C, c2 As C) on C:  c1.ID = 42, c2.ID = 1491
'Shared method M4(f As F, c As C) on F:  c.ID = 1491
'

另请参阅

适用于

CreateDelegate(Type, Type, String, Boolean, Boolean)

Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs

创建一个指定类型的委托,该委托表示指定类的指定静态方法,指定区分大小写,以及无法绑定的指定行为。

public:
 static Delegate ^ CreateDelegate(Type ^ type, Type ^ target, System::String ^ method, bool ignoreCase, bool throwOnBindFailure);
public static Delegate? CreateDelegate(Type type, Type target, string method, bool ignoreCase, bool throwOnBindFailure);
[System.Diagnostics.CodeAnalysis.RequiresUnreferencedCode("The target method might be removed")]
public static Delegate? CreateDelegate(Type type, Type target, string method, bool ignoreCase, bool throwOnBindFailure);
public static Delegate CreateDelegate(Type type, Type target, string method, bool ignoreCase, bool throwOnBindFailure);
static member CreateDelegate : Type * Type * string * bool * bool -> Delegate
[<System.Diagnostics.CodeAnalysis.RequiresUnreferencedCode("The target method might be removed")>]
static member CreateDelegate : Type * Type * string * bool * bool -> Delegate
Public Shared Function CreateDelegate (type As Type, target As Type, method As String, ignoreCase As Boolean, throwOnBindFailure As Boolean) As Delegate

参数

type
Type

Type要创建的委托。

target
Type

Type表示实现method的类。

method
String

委托要表示的静态方法的名称。

ignoreCase
Boolean

一个布尔值,指示在比较方法名称时是否忽略大小写。

throwOnBindFailure
Boolean

如果 无法绑定,则为 ;否则为 >。

返回

表示指定类的指定静态方法的委托。

属性

例外

typenull

-或-

targetnull

-或-

methodnull

type 不继承 MulticastDelegate

-或-

type不是 .RuntimeType 请参阅 反射中的运行时类型

-或-

target不是 .RuntimeType

-或-

target 是一种打开的泛型类型。 也就是说,其 ContainsGenericParameters 属性为 true.

-或-

method 不是 static 方法(Visual Basic中的 Shared 方法)。

-或-

method 无法绑定,例如,因为它找不到,并且 throwOnBindFailuretrue

Invoke找不到方法type

调用方没有访问 method所需的权限。

注解

此方法仅为静态方法创建委托。 实例方法是与类实例关联的方法;静态方法是与类本身关联的方法。

另请参阅

适用于

CreateDelegate(Type, MethodInfo, Boolean)

Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs
Source:
Delegate.CoreCLR.cs

创建指定类型的委托来表示指定的静态方法,并指定了绑定失败时的行为。

public:
 static Delegate ^ CreateDelegate(Type ^ type, System::Reflection::MethodInfo ^ method, bool throwOnBindFailure);
public static Delegate? CreateDelegate(Type type, System.Reflection.MethodInfo method, bool throwOnBindFailure);
public static Delegate CreateDelegate(Type type, System.Reflection.MethodInfo method, bool throwOnBindFailure);
static member CreateDelegate : Type * System.Reflection.MethodInfo * bool -> Delegate
Public Shared Function CreateDelegate (type As Type, method As MethodInfo, throwOnBindFailure As Boolean) As Delegate

参数

type
Type

Type要创建的委托。

method
MethodInfo

MethodInfo描述委托要表示的静态或实例方法。

throwOnBindFailure
Boolean

如果 无法绑定,则为 ;否则为 >。

返回

表示指定静态方法的指定类型的委托。

例外

typenull

-或-

methodnull

type 不继承 MulticastDelegate

-或-

type不是 .RuntimeType 请参阅 反射中的运行时类型

-或-

method 不能绑定,并且 throwOnBindFailuretrue

-或-

method不是 .RuntimeMethodInfo 请参阅 反射中的运行时类型

Invoke找不到方法type

调用方没有访问 method所需的权限。

示例

本部分包含两个代码示例。 第一个示例演示了可以使用此方法重载创建的两种类型的委托:在实例方法上打开并打开静态方法。

第二个代码示例演示了兼容的参数类型和返回类型。

示例 1

以下代码示例演示了使用 CreateDelegate 方法的这个重载来创建委托的两种方式。

注释

CreateDelegate 方法有两个重载,它们指定一个 MethodInfo 但没有指定第一个参数;它们的功能相同,只是其中一个允许你指定在绑定失败时是否引发异常,而另一个则始终会引发异常。 此代码示例使用这两个重载。

该示例声明类C,带有静态方法M2和实例方法M1,以及两种委托类型:D1 使用类的实例C和一个字符串,D2 使用一个字符串。

第二个名为Example的类包含用于创建委托的代码。

  • 为实例方法 D1 创建了一个类型为 M1 的委托,代表一个开放实例方法。 调用委托时必须传递一个实例。
  • 为静态方法 D2 创建类型 M2 的委托,该委托表示开放的静态方法。
using System;
using System.Reflection;

// Declare three delegate types for demonstrating the combinations
// of static versus instance methods and open versus closed
// delegates.
//
public delegate void D1(C c, string s);
public delegate void D2(string s);
public delegate void D3();

// A sample class with an instance method and a static method.
//
public class C
{
    private int id;
    public C(int id) { this.id = id; }

    public void M1(string s) =>
        Console.WriteLine($"Instance method M1 on C:  id = {this.id}, s = {s}");

    public static void M2(string s)
    {
        Console.WriteLine($"Static method M2 on C:  s = {s}");
    }
}

public class Example2
{
    public static void Main()
    {
        C c1 = new C(42);

        // Get a MethodInfo for each method.
        //
        MethodInfo mi1 = typeof(C).GetMethod("M1",
            BindingFlags.Public | BindingFlags.Instance);
        MethodInfo mi2 = typeof(C).GetMethod("M2",
            BindingFlags.Public | BindingFlags.Static);

        D1 d1;
        D2 d2;
        D3 d3;

        Console.WriteLine("\nAn instance method closed over C.");
        // In this case, the delegate and the
        // method must have the same list of argument types; use
        // delegate type D2 with instance method M1.
        //
        Delegate test =
            Delegate.CreateDelegate(typeof(D2), c1, mi1, false);

        // Because false was specified for throwOnBindFailure
        // in the call to CreateDelegate, the variable 'test'
        // contains null if the method fails to bind (for
        // example, if mi1 happened to represent a method of
        // some class other than C).
        //
        if (test != null)
        {
            d2 = (D2)test;

            // The same instance of C is used every time the
            // delegate is invoked.
            d2("Hello, World!");
            d2("Hi, Mom!");
        }

        Console.WriteLine("\nAn open instance method.");
        // In this case, the delegate has one more
        // argument than the instance method; this argument comes
        // at the beginning, and represents the hidden instance
        // argument of the instance method. Use delegate type D1
        // with instance method M1.
        //
        d1 = (D1)Delegate.CreateDelegate(typeof(D1), null, mi1);

        // An instance of C must be passed in each time the
        // delegate is invoked.
        //
        d1(c1, "Hello, World!");
        d1(new C(5280), "Hi, Mom!");

        Console.WriteLine("\nAn open static method.");
        // In this case, the delegate and the method must
        // have the same list of argument types; use delegate type
        // D2 with static method M2.
        //
        d2 = (D2)Delegate.CreateDelegate(typeof(D2), null, mi2);

        // No instances of C are involved, because this is a static
        // method.
        //
        d2("Hello, World!");
        d2("Hi, Mom!");

        Console.WriteLine("\nA static method closed over the first argument (String).");
        // The delegate must omit the first argument of the method.
        // A string is passed as the firstArgument parameter, and
        // the delegate is bound to this string. Use delegate type
        // D3 with static method M2.
        //
        d3 = (D3)Delegate.CreateDelegate(typeof(D3),
            "Hello, World!", mi2);

        // Each time the delegate is invoked, the same string is
        // used.
        d3();
    }
}

/* This code example produces the following output:

An instance method closed over C.
Instance method M1 on C:  id = 42, s = Hello, World!
Instance method M1 on C:  id = 42, s = Hi, Mom!

An open instance method.
Instance method M1 on C:  id = 42, s = Hello, World!
Instance method M1 on C:  id = 5280, s = Hi, Mom!

An open static method.
Static method M2 on C:  s = Hello, World!
Static method M2 on C:  s = Hi, Mom!

A static method closed over the first argument (String).
Static method M2 on C:  s = Hello, World!
 */
open System
open System.Reflection

// A sample class with an instance method and a static method.
type C(id) =
    member _.M1(s) =
        printfn $"Instance method M1 on C:  id = %i{id}, s = %s{s}"

    static member M2(s) =
        printfn $"Static method M2 on C:  s = %s{s}"
    
// Declare three delegate types for demonstrating the combinations
// of static versus instance methods and open versus closed
// delegates.
type D1 = delegate of C * string -> unit
type D2 = delegate of string -> unit
type D3 = delegate of unit -> unit

let c1 = C 42

// Get a MethodInfo for each method.
//
let mi1 = typeof<C>.GetMethod("M1", BindingFlags.Public ||| BindingFlags.Instance)
let mi2 = typeof<C>.GetMethod("M2", BindingFlags.Public ||| BindingFlags.Static)

printfn "\nAn instance method closed over C."

// In this case, the delegate and the
// method must have the same list of argument types use
// delegate type D2 with instance method M1.
let test = Delegate.CreateDelegate(typeof<D2>, c1, mi1, false)

// Because false was specified for throwOnBindFailure
// in the call to CreateDelegate, the variable 'test'
// contains null if the method fails to bind (for
// example, if mi1 happened to represent a method of
// some class other than C).
if test <> null then
    let d2 = test :?> D2

    // The same instance of C is used every time the
    // delegate is invoked.
    d2.Invoke "Hello, World!"
    d2.Invoke "Hi, Mom!"

printfn "\nAn open instance method."

// In this case, the delegate has one more
// argument than the instance method this argument comes
// at the beginning, and represents the hidden instance
// argument of the instance method. Use delegate type D1
// with instance method M1.
let d1 = Delegate.CreateDelegate(typeof<D1>, null, mi1) :?> D1

// An instance of C must be passed in each time the
// delegate is invoked.
d1.Invoke(c1, "Hello, World!")
d1.Invoke(C 5280, "Hi, Mom!")

printfn "\nAn open static method."
// In this case, the delegate and the method must
// have the same list of argument types use delegate type
// D2 with static method M2.
let d2 = Delegate.CreateDelegate(typeof<D2>, null, mi2) :?> D2

// No instances of C are involved, because this is a static
// method.
d2.Invoke "Hello, World!"
d2.Invoke "Hi, Mom!"

printfn "\nA static method closed over the first argument (String)."
// The delegate must omit the first argument of the method.
// A string is passed as the firstArgument parameter, and
// the delegate is bound to this string. Use delegate type
// D3 with static method M2.
let d3 = Delegate.CreateDelegate(typeof<D3>, "Hello, World!", mi2) :?> D3

// Each time the delegate is invoked, the same string is used.
d3.Invoke()

// This code example produces the following output:
//     An instance method closed over C.
//     Instance method M1 on C:  id = 42, s = Hello, World!
//     Instance method M1 on C:  id = 42, s = Hi, Mom!
//     
//     An open instance method.
//     Instance method M1 on C:  id = 42, s = Hello, World!
//     Instance method M1 on C:  id = 5280, s = Hi, Mom!
//     
//     An open static method.
//     Static method M2 on C:  s = Hello, World!
//     Static method M2 on C:  s = Hi, Mom!
//     
//     A static method closed over the first argument (String).
//     Static method M2 on C:  s = Hello, World!
Imports System.Reflection
Imports System.Security.Permissions

' Declare three delegate types for demonstrating the combinations
' of Shared versus instance methods and open versus closed
' delegates.
'
Public Delegate Sub D1(ByVal c As C2, ByVal s As String)
Public Delegate Sub D2(ByVal s As String)
Public Delegate Sub D3()

' A sample class with an instance method and a Shared method.
'
Public Class C2
    Private id As Integer
    Public Sub New(ByVal id As Integer)
        Me.id = id
    End Sub

    Public Sub M1(ByVal s As String)
        Console.WriteLine("Instance method M1 on C2:  id = {0}, s = {1}",
            Me.id, s)
    End Sub

    Public Shared Sub M2(ByVal s As String)
        Console.WriteLine("Shared method M2 on C2:  s = {0}", s)
    End Sub
End Class

Public Class Example2

    Public Shared Sub Main()

        Dim c1 As New C2(42)

        ' Get a MethodInfo for each method.
        '
        Dim mi1 As MethodInfo = GetType(C2).GetMethod("M1",
            BindingFlags.Public Or BindingFlags.Instance)
        Dim mi2 As MethodInfo = GetType(C2).GetMethod("M2",
            BindingFlags.Public Or BindingFlags.Static)

        Dim d1 As D1
        Dim d2 As D2
        Dim d3 As D3


        Console.WriteLine(vbLf & "An instance method closed over C2.")
        ' In this case, the delegate and the
        ' method must have the same list of argument types; use
        ' delegate type D2 with instance method M1.
        '
        Dim test As [Delegate] =
            [Delegate].CreateDelegate(GetType(D2), c1, mi1, False)

        ' Because False was specified for throwOnBindFailure 
        ' in the call to CreateDelegate, the variable 'test'
        ' contains Nothing if the method fails to bind (for 
        ' example, if mi1 happened to represent a method of 
        ' some class other than C2).
        '
        If test IsNot Nothing Then
            d2 = CType(test, D2)

            ' The same instance of C2 is used every time the
            ' delegate is invoked.
            d2("Hello, World!")
            d2("Hi, Mom!")
        End If


        Console.WriteLine(vbLf & "An open instance method.")
        ' In this case, the delegate has one more 
        ' argument than the instance method; this argument comes
        ' at the beginning, and represents the hidden instance
        ' argument of the instance method. Use delegate type D1
        ' with instance method M1.
        '
        d1 = CType([Delegate].CreateDelegate(GetType(D1), Nothing, mi1), D1)

        ' An instance of C2 must be passed in each time the 
        ' delegate is invoked.
        '
        d1(c1, "Hello, World!")
        d1(New C2(5280), "Hi, Mom!")


        Console.WriteLine(vbLf & "An open Shared method.")
        ' In this case, the delegate and the method must 
        ' have the same list of argument types; use delegate type
        ' D2 with Shared method M2.
        '
        d2 = CType([Delegate].CreateDelegate(GetType(D2), Nothing, mi2), D2)

        ' No instances of C2 are involved, because this is a Shared
        ' method. 
        '
        d2("Hello, World!")
        d2("Hi, Mom!")


        Console.WriteLine(vbLf & "A Shared method closed over the first argument (String).")
        ' The delegate must omit the first argument of the method.
        ' A string is passed as the firstArgument parameter, and 
        ' the delegate is bound to this string. Use delegate type 
        ' D3 with Shared method M2. 
        '
        d3 = CType([Delegate].CreateDelegate(GetType(D3), "Hello, World!", mi2), D3)

        ' Each time the delegate is invoked, the same string is
        ' used.
        d3()

    End Sub
End Class

' This code example produces the following output:
'
'An instance method closed over C2.
'Instance method M1 on C2:  id = 42, s = Hello, World!
'Instance method M1 on C2:  id = 42, s = Hi, Mom!
'
'An open instance method.
'Instance method M1 on C2:  id = 42, s = Hello, World!
'Instance method M1 on C2:  id = 5280, s = Hi, Mom!
'
'An open Shared method.
'Shared method M2 on C2:  s = Hello, World!
'Shared method M2 on C2:  s = Hi, Mom!
'
'A Shared method closed over the first argument (String).
'Shared method M2 on C2:  s = Hello, World!
'

示例 2

下面的代码示例演示参数类型和返回类型的兼容性。

该代码示例定义了一个基类,命名为 Base,以及一个命名为 Derived 的类继承自 Base。 派生类有一个名为 staticShared(在 Visual Basic 中为 MyMethod)方法,该方法有一个类型为 Base 的参数,返回类型为 Derived。 该代码示例还定义了一个名为 Example 的委托,该委托具有一个类型为 Derived 的参数和一个类型为 Base 的返回值。

代码示例演示如何使用命名 Example 的委托来表示方法 MyMethod。 该方法可以绑定到委托,原因如下:

  • 委托()的参数类型比 (DerivedMyMethod) 的参数类型Base更严格,以便始终安全地将委托的参数传递给 MyMethod
  • MyMethod (Derived) 的返回类型比委托 (Base) 的参数类型更严格,因此将方法的返回类型强制转换为委托的返回类型始终是安全的。

该代码示例不生成任何输出。

using System;
using System.Reflection;

// Define two classes to use in the demonstration, a base class and
// a class that derives from it.
//
public class Base { }

public class Derived : Base
{
    // Define a static method to use in the demonstration. The method
    // takes an instance of Base and returns an instance of Derived.
    // For the purposes of the demonstration, it is not necessary for
    // the method to do anything useful.
    //
    public static Derived MyMethod(Base arg)
    {
        Base dummy = arg;
        return new Derived();
    }
}

// Define a delegate that takes an instance of Derived and returns an
// instance of Base.
//
public delegate Base Example5(Derived arg);

class Test
{
    public static void Main()
    {
        // The binding flags needed to retrieve MyMethod.
        BindingFlags flags = BindingFlags.Public | BindingFlags.Static;

        // Get a MethodInfo that represents MyMethod.
        MethodInfo minfo = typeof(Derived).GetMethod("MyMethod", flags);

        // Demonstrate contravariance of parameter types and covariance
        // of return types by using the delegate Example5 to represent
        // MyMethod. The delegate binds to the method because the
        // parameter of the delegate is more restrictive than the
        // parameter of the method (that is, the delegate accepts an
        // instance of Derived, which can always be safely passed to
        // a parameter of type Base), and the return type of MyMethod
        // is more restrictive than the return type of Example5 (that
        // is, the method returns an instance of Derived, which can
        // always be safely cast to type Base).
        //
        Example5 ex =
            (Example5)Delegate.CreateDelegate(typeof(Example5), minfo);

        // Execute MyMethod using the delegate Example5.
        //
        Base b = ex(new Derived());
    }
}
open System
open System.Reflection

// Define two classes to use in the demonstration, a base class and
// a class that derives from it.
type Base() = class end

type Derived() =
    inherit Base()

    // Define a static method to use in the demonstration. The method
    // takes an instance of Base and returns an instance of Derived.
    // For the purposes of the demonstration, it is not necessary for
    // the method to do anything useful.
    static member MyMethod(arg: Base) =
        Derived()

// Define a delegate that takes an instance of Derived and returns an
// instance of Base.
type Example = delegate of Derived -> Base

// The binding flags needed to retrieve MyMethod.
let flags = BindingFlags.Public ||| BindingFlags.Static

// Get a MethodInfo that represents MyMethod.
let minfo = typeof<Derived>.GetMethod("MyMethod", flags)

// Demonstrate contravariance of parameter types and covariance
// of return types by using the delegate Example to represent
// MyMethod. The delegate binds to the method because the
// parameter of the delegate is more restrictive than the
// parameter of the method (that is, the delegate accepts an
// instance of Derived, which can always be safely passed to
// a parameter of type Base), and the return type of MyMethod
// is more restrictive than the return type of Example (that
// is, the method returns an instance of Derived, which can
// always be safely cast to type Base).
let ex = Delegate.CreateDelegate(typeof<Example>, minfo) :?> Example

// Execute MyMethod using the delegate Example.
let b = Derived() |> ex.Invoke
Imports System.Reflection

' Define two classes to use in the demonstration, a base class and 
' a class that derives from it.
'
Public Class Base
End Class

Public Class Derived
    Inherits Base

    ' Define a Shared method to use in the demonstration. The method 
    ' takes an instance of Base and returns an instance of Derived.  
    ' For the purposes of the demonstration, it is not necessary for 
    ' the method to do anything useful. 
    '
    Public Shared Function MyMethod(ByVal arg As Base) As Derived
        Dim dummy As Base = arg
        Return New Derived()
    End Function

End Class

' Define a delegate that takes an instance of Derived and returns an
' instance of Base.
'
Public Delegate Function Example(ByVal arg As Derived) As Base

Module Test

    Sub Main()

        ' The binding flags needed to retrieve MyMethod.
        Dim flags As BindingFlags = _
            BindingFlags.Public Or BindingFlags.Static

        ' Get a MethodInfo that represents MyMethod.
        Dim minfo As MethodInfo = _
            GetType(Derived).GetMethod("MyMethod", flags)

        ' Demonstrate contravariance of parameter types and covariance
        ' of return types by using the delegate Example to represent
        ' MyMethod. The delegate binds to the method because the
        ' parameter of the delegate is more restrictive than the 
        ' parameter of the method (that is, the delegate accepts an
        ' instance of Derived, which can always be safely passed to
        ' a parameter of type Base), and the return type of MyMethod
        ' is more restrictive than the return type of Example (that
        ' is, the method returns an instance of Derived, which can
        ' always be safely cast to type Base). 
        '
        Dim ex As Example = CType( _
            [Delegate].CreateDelegate(GetType(Example), minfo), _
            Example _
        )

        ' Execute MyMethod using the delegate Example.
        '        
        Dim b As Base = ex(New Derived())
    End Sub
End Module

注解

此方法重载可以创建打开的静态方法委托和打开的实例方法委托 ,即公开实例方法隐藏的第一个参数的委托。 有关详细说明,请参阅更常规 CreateDelegate(Type, Object, MethodInfo, Boolean) 的方法重载,以便为实例或静态方法创建打开或关闭的委托的所有组合。

注释

当委托未在其第一个参数上关闭时,应使用此方法重载,因为在这种情况下,此方法重载的速度会稍快一些。

另请参阅

适用于

CreateDelegate(Type, Object, String)

Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs

创建表示在指定类实例上调用的指定实例方法的指定类型的委托。

public:
 static Delegate ^ CreateDelegate(Type ^ type, System::Object ^ target, System::String ^ method);
[System.Diagnostics.CodeAnalysis.RequiresUnreferencedCode("The target method might be removed")]
public static Delegate CreateDelegate(Type type, object target, string method);
public static Delegate CreateDelegate(Type type, object target, string method);
[<System.Diagnostics.CodeAnalysis.RequiresUnreferencedCode("The target method might be removed")>]
static member CreateDelegate : Type * obj * string -> Delegate
static member CreateDelegate : Type * obj * string -> Delegate
Public Shared Function CreateDelegate (type As Type, target As Object, method As String) As Delegate

参数

type
Type

Type要创建的委托。

target
Object

对其调用的 method 类实例。

method
String

委托要表示的实例方法的名称。

返回

指定类型的委托,表示在指定类实例上调用的指定实例方法。

属性

例外

typenull

-或-

targetnull

-或-

methodnull

type 不继承 MulticastDelegate

-或-

type不是 .RuntimeType 请参阅 反射中的运行时类型

-或-

method 不是实例方法。

-或-

method 无法绑定,例如,因为它找不到。

Invoke找不到方法type

调用方没有访问 method所需的权限。

注解

此方法仅为实例方法创建委托。 实例方法是与类实例关联的方法;静态方法是与类本身关联的方法。

此方法重载等效于调用CreateDelegate(Type, Object, String, Boolean, Boolean)方法重载,指定falseignoreCasetrue指定throwOnBindFailure方法重载。

另请参阅

适用于

CreateDelegate(Type, Object, MethodInfo)

Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs

使用指定的第一个参数创建表示指定静态或实例方法的指定类型的委托。

public:
 static Delegate ^ CreateDelegate(Type ^ type, System::Object ^ firstArgument, System::Reflection::MethodInfo ^ method);
public static Delegate CreateDelegate(Type type, object? firstArgument, System.Reflection.MethodInfo method);
public static Delegate CreateDelegate(Type type, object firstArgument, System.Reflection.MethodInfo method);
static member CreateDelegate : Type * obj * System.Reflection.MethodInfo -> Delegate
Public Shared Function CreateDelegate (type As Type, firstArgument As Object, method As MethodInfo) As Delegate

参数

type
Type

Type要创建的委托。

firstArgument
Object

委托绑定到的对象,或nullmethod 视为 staticShared in Visual Basic)。

method
MethodInfo

MethodInfo描述委托要表示的静态或实例方法。

返回

表示指定静态或实例方法的指定类型的委托。

例外

typenull

-或-

methodnull

type 不继承 MulticastDelegate

-或-

type不是 .RuntimeType 请参阅 反射中的运行时类型

-或-

method 无法绑定。

-或-

method不是 .RuntimeMethodInfo 请参阅 反射中的运行时类型

Invoke找不到方法type

调用方没有访问 method所需的权限。

示例

本部分包含两个代码示例。 第一个示例演示了可以使用此方法重载创建的两种类型的委托:在实例方法上打开并打开静态方法。

第二个代码示例演示了兼容的参数类型和返回类型。

示例 1

以下代码示例演示了使用 CreateDelegate 方法的这个重载来创建委托的两种方式。

注释

CreateDelegate 方法有两个重载,它们指定一个 MethodInfo 但没有指定第一个参数;它们的功能相同,只是其中一个允许你指定在绑定失败时是否引发异常,而另一个则始终会引发异常。 此代码示例使用这两个重载。

该示例声明类C,带有静态方法M2和实例方法M1,以及两种委托类型:D1 使用类的实例C和一个字符串,D2 使用一个字符串。

第二个名为Example的类包含用于创建委托的代码。

  • 为实例方法 D1 创建了一个类型为 M1 的委托,代表一个开放实例方法。 调用委托时必须传递一个实例。
  • 为静态方法 D2 创建类型 M2 的委托,该委托表示开放的静态方法。
using System;
using System.Reflection;

// Declare three delegate types for demonstrating the combinations
// of static versus instance methods and open versus closed
// delegates.
//
public delegate void D1(C c, string s);
public delegate void D2(string s);
public delegate void D3();

// A sample class with an instance method and a static method.
//
public class C
{
    private int id;
    public C(int id) { this.id = id; }

    public void M1(string s) =>
        Console.WriteLine($"Instance method M1 on C:  id = {this.id}, s = {s}");

    public static void M2(string s)
    {
        Console.WriteLine($"Static method M2 on C:  s = {s}");
    }
}

public class Example2
{
    public static void Main()
    {
        C c1 = new C(42);

        // Get a MethodInfo for each method.
        //
        MethodInfo mi1 = typeof(C).GetMethod("M1",
            BindingFlags.Public | BindingFlags.Instance);
        MethodInfo mi2 = typeof(C).GetMethod("M2",
            BindingFlags.Public | BindingFlags.Static);

        D1 d1;
        D2 d2;
        D3 d3;

        Console.WriteLine("\nAn instance method closed over C.");
        // In this case, the delegate and the
        // method must have the same list of argument types; use
        // delegate type D2 with instance method M1.
        //
        Delegate test =
            Delegate.CreateDelegate(typeof(D2), c1, mi1, false);

        // Because false was specified for throwOnBindFailure
        // in the call to CreateDelegate, the variable 'test'
        // contains null if the method fails to bind (for
        // example, if mi1 happened to represent a method of
        // some class other than C).
        //
        if (test != null)
        {
            d2 = (D2)test;

            // The same instance of C is used every time the
            // delegate is invoked.
            d2("Hello, World!");
            d2("Hi, Mom!");
        }

        Console.WriteLine("\nAn open instance method.");
        // In this case, the delegate has one more
        // argument than the instance method; this argument comes
        // at the beginning, and represents the hidden instance
        // argument of the instance method. Use delegate type D1
        // with instance method M1.
        //
        d1 = (D1)Delegate.CreateDelegate(typeof(D1), null, mi1);

        // An instance of C must be passed in each time the
        // delegate is invoked.
        //
        d1(c1, "Hello, World!");
        d1(new C(5280), "Hi, Mom!");

        Console.WriteLine("\nAn open static method.");
        // In this case, the delegate and the method must
        // have the same list of argument types; use delegate type
        // D2 with static method M2.
        //
        d2 = (D2)Delegate.CreateDelegate(typeof(D2), null, mi2);

        // No instances of C are involved, because this is a static
        // method.
        //
        d2("Hello, World!");
        d2("Hi, Mom!");

        Console.WriteLine("\nA static method closed over the first argument (String).");
        // The delegate must omit the first argument of the method.
        // A string is passed as the firstArgument parameter, and
        // the delegate is bound to this string. Use delegate type
        // D3 with static method M2.
        //
        d3 = (D3)Delegate.CreateDelegate(typeof(D3),
            "Hello, World!", mi2);

        // Each time the delegate is invoked, the same string is
        // used.
        d3();
    }
}

/* This code example produces the following output:

An instance method closed over C.
Instance method M1 on C:  id = 42, s = Hello, World!
Instance method M1 on C:  id = 42, s = Hi, Mom!

An open instance method.
Instance method M1 on C:  id = 42, s = Hello, World!
Instance method M1 on C:  id = 5280, s = Hi, Mom!

An open static method.
Static method M2 on C:  s = Hello, World!
Static method M2 on C:  s = Hi, Mom!

A static method closed over the first argument (String).
Static method M2 on C:  s = Hello, World!
 */
open System
open System.Reflection

// A sample class with an instance method and a static method.
type C(id) =
    member _.M1(s) =
        printfn $"Instance method M1 on C:  id = %i{id}, s = %s{s}"

    static member M2(s) =
        printfn $"Static method M2 on C:  s = %s{s}"
    
// Declare three delegate types for demonstrating the combinations
// of static versus instance methods and open versus closed
// delegates.
type D1 = delegate of C * string -> unit
type D2 = delegate of string -> unit
type D3 = delegate of unit -> unit

let c1 = C 42

// Get a MethodInfo for each method.
//
let mi1 = typeof<C>.GetMethod("M1", BindingFlags.Public ||| BindingFlags.Instance)
let mi2 = typeof<C>.GetMethod("M2", BindingFlags.Public ||| BindingFlags.Static)

printfn "\nAn instance method closed over C."

// In this case, the delegate and the
// method must have the same list of argument types use
// delegate type D2 with instance method M1.
let test = Delegate.CreateDelegate(typeof<D2>, c1, mi1, false)

// Because false was specified for throwOnBindFailure
// in the call to CreateDelegate, the variable 'test'
// contains null if the method fails to bind (for
// example, if mi1 happened to represent a method of
// some class other than C).
if test <> null then
    let d2 = test :?> D2

    // The same instance of C is used every time the
    // delegate is invoked.
    d2.Invoke "Hello, World!"
    d2.Invoke "Hi, Mom!"

printfn "\nAn open instance method."

// In this case, the delegate has one more
// argument than the instance method this argument comes
// at the beginning, and represents the hidden instance
// argument of the instance method. Use delegate type D1
// with instance method M1.
let d1 = Delegate.CreateDelegate(typeof<D1>, null, mi1) :?> D1

// An instance of C must be passed in each time the
// delegate is invoked.
d1.Invoke(c1, "Hello, World!")
d1.Invoke(C 5280, "Hi, Mom!")

printfn "\nAn open static method."
// In this case, the delegate and the method must
// have the same list of argument types use delegate type
// D2 with static method M2.
let d2 = Delegate.CreateDelegate(typeof<D2>, null, mi2) :?> D2

// No instances of C are involved, because this is a static
// method.
d2.Invoke "Hello, World!"
d2.Invoke "Hi, Mom!"

printfn "\nA static method closed over the first argument (String)."
// The delegate must omit the first argument of the method.
// A string is passed as the firstArgument parameter, and
// the delegate is bound to this string. Use delegate type
// D3 with static method M2.
let d3 = Delegate.CreateDelegate(typeof<D3>, "Hello, World!", mi2) :?> D3

// Each time the delegate is invoked, the same string is used.
d3.Invoke()

// This code example produces the following output:
//     An instance method closed over C.
//     Instance method M1 on C:  id = 42, s = Hello, World!
//     Instance method M1 on C:  id = 42, s = Hi, Mom!
//     
//     An open instance method.
//     Instance method M1 on C:  id = 42, s = Hello, World!
//     Instance method M1 on C:  id = 5280, s = Hi, Mom!
//     
//     An open static method.
//     Static method M2 on C:  s = Hello, World!
//     Static method M2 on C:  s = Hi, Mom!
//     
//     A static method closed over the first argument (String).
//     Static method M2 on C:  s = Hello, World!
Imports System.Reflection
Imports System.Security.Permissions

' Declare three delegate types for demonstrating the combinations
' of Shared versus instance methods and open versus closed
' delegates.
'
Public Delegate Sub D1(ByVal c As C2, ByVal s As String)
Public Delegate Sub D2(ByVal s As String)
Public Delegate Sub D3()

' A sample class with an instance method and a Shared method.
'
Public Class C2
    Private id As Integer
    Public Sub New(ByVal id As Integer)
        Me.id = id
    End Sub

    Public Sub M1(ByVal s As String)
        Console.WriteLine("Instance method M1 on C2:  id = {0}, s = {1}",
            Me.id, s)
    End Sub

    Public Shared Sub M2(ByVal s As String)
        Console.WriteLine("Shared method M2 on C2:  s = {0}", s)
    End Sub
End Class

Public Class Example2

    Public Shared Sub Main()

        Dim c1 As New C2(42)

        ' Get a MethodInfo for each method.
        '
        Dim mi1 As MethodInfo = GetType(C2).GetMethod("M1",
            BindingFlags.Public Or BindingFlags.Instance)
        Dim mi2 As MethodInfo = GetType(C2).GetMethod("M2",
            BindingFlags.Public Or BindingFlags.Static)

        Dim d1 As D1
        Dim d2 As D2
        Dim d3 As D3


        Console.WriteLine(vbLf & "An instance method closed over C2.")
        ' In this case, the delegate and the
        ' method must have the same list of argument types; use
        ' delegate type D2 with instance method M1.
        '
        Dim test As [Delegate] =
            [Delegate].CreateDelegate(GetType(D2), c1, mi1, False)

        ' Because False was specified for throwOnBindFailure 
        ' in the call to CreateDelegate, the variable 'test'
        ' contains Nothing if the method fails to bind (for 
        ' example, if mi1 happened to represent a method of 
        ' some class other than C2).
        '
        If test IsNot Nothing Then
            d2 = CType(test, D2)

            ' The same instance of C2 is used every time the
            ' delegate is invoked.
            d2("Hello, World!")
            d2("Hi, Mom!")
        End If


        Console.WriteLine(vbLf & "An open instance method.")
        ' In this case, the delegate has one more 
        ' argument than the instance method; this argument comes
        ' at the beginning, and represents the hidden instance
        ' argument of the instance method. Use delegate type D1
        ' with instance method M1.
        '
        d1 = CType([Delegate].CreateDelegate(GetType(D1), Nothing, mi1), D1)

        ' An instance of C2 must be passed in each time the 
        ' delegate is invoked.
        '
        d1(c1, "Hello, World!")
        d1(New C2(5280), "Hi, Mom!")


        Console.WriteLine(vbLf & "An open Shared method.")
        ' In this case, the delegate and the method must 
        ' have the same list of argument types; use delegate type
        ' D2 with Shared method M2.
        '
        d2 = CType([Delegate].CreateDelegate(GetType(D2), Nothing, mi2), D2)

        ' No instances of C2 are involved, because this is a Shared
        ' method. 
        '
        d2("Hello, World!")
        d2("Hi, Mom!")


        Console.WriteLine(vbLf & "A Shared method closed over the first argument (String).")
        ' The delegate must omit the first argument of the method.
        ' A string is passed as the firstArgument parameter, and 
        ' the delegate is bound to this string. Use delegate type 
        ' D3 with Shared method M2. 
        '
        d3 = CType([Delegate].CreateDelegate(GetType(D3), "Hello, World!", mi2), D3)

        ' Each time the delegate is invoked, the same string is
        ' used.
        d3()

    End Sub
End Class

' This code example produces the following output:
'
'An instance method closed over C2.
'Instance method M1 on C2:  id = 42, s = Hello, World!
'Instance method M1 on C2:  id = 42, s = Hi, Mom!
'
'An open instance method.
'Instance method M1 on C2:  id = 42, s = Hello, World!
'Instance method M1 on C2:  id = 5280, s = Hi, Mom!
'
'An open Shared method.
'Shared method M2 on C2:  s = Hello, World!
'Shared method M2 on C2:  s = Hi, Mom!
'
'A Shared method closed over the first argument (String).
'Shared method M2 on C2:  s = Hello, World!
'

示例 2

下面的代码示例演示参数类型和返回类型的兼容性。

该代码示例定义了一个基类,命名为 Base,以及一个命名为 Derived 的类继承自 Base。 派生类有一个名为 staticShared(在 Visual Basic 中为 MyMethod)方法,该方法有一个类型为 Base 的参数,返回类型为 Derived。 该代码示例还定义了一个名为 Example 的委托,该委托具有一个类型为 Derived 的参数和一个类型为 Base 的返回值。

代码示例演示如何使用命名 Example 的委托来表示方法 MyMethod。 该方法可以绑定到委托,原因如下:

  • 委托()的参数类型比 (DerivedMyMethod) 的参数类型Base更严格,以便始终安全地将委托的参数传递给 MyMethod
  • MyMethod (Derived) 的返回类型比委托 (Base) 的参数类型更严格,因此将方法的返回类型强制转换为委托的返回类型始终是安全的。

该代码示例不生成任何输出。

using System;
using System.Reflection;

// Define two classes to use in the demonstration, a base class and
// a class that derives from it.
//
public class Base { }

public class Derived : Base
{
    // Define a static method to use in the demonstration. The method
    // takes an instance of Base and returns an instance of Derived.
    // For the purposes of the demonstration, it is not necessary for
    // the method to do anything useful.
    //
    public static Derived MyMethod(Base arg)
    {
        Base dummy = arg;
        return new Derived();
    }
}

// Define a delegate that takes an instance of Derived and returns an
// instance of Base.
//
public delegate Base Example5(Derived arg);

class Test
{
    public static void Main()
    {
        // The binding flags needed to retrieve MyMethod.
        BindingFlags flags = BindingFlags.Public | BindingFlags.Static;

        // Get a MethodInfo that represents MyMethod.
        MethodInfo minfo = typeof(Derived).GetMethod("MyMethod", flags);

        // Demonstrate contravariance of parameter types and covariance
        // of return types by using the delegate Example5 to represent
        // MyMethod. The delegate binds to the method because the
        // parameter of the delegate is more restrictive than the
        // parameter of the method (that is, the delegate accepts an
        // instance of Derived, which can always be safely passed to
        // a parameter of type Base), and the return type of MyMethod
        // is more restrictive than the return type of Example5 (that
        // is, the method returns an instance of Derived, which can
        // always be safely cast to type Base).
        //
        Example5 ex =
            (Example5)Delegate.CreateDelegate(typeof(Example5), minfo);

        // Execute MyMethod using the delegate Example5.
        //
        Base b = ex(new Derived());
    }
}
open System
open System.Reflection

// Define two classes to use in the demonstration, a base class and
// a class that derives from it.
type Base() = class end

type Derived() =
    inherit Base()

    // Define a static method to use in the demonstration. The method
    // takes an instance of Base and returns an instance of Derived.
    // For the purposes of the demonstration, it is not necessary for
    // the method to do anything useful.
    static member MyMethod(arg: Base) =
        Derived()

// Define a delegate that takes an instance of Derived and returns an
// instance of Base.
type Example = delegate of Derived -> Base

// The binding flags needed to retrieve MyMethod.
let flags = BindingFlags.Public ||| BindingFlags.Static

// Get a MethodInfo that represents MyMethod.
let minfo = typeof<Derived>.GetMethod("MyMethod", flags)

// Demonstrate contravariance of parameter types and covariance
// of return types by using the delegate Example to represent
// MyMethod. The delegate binds to the method because the
// parameter of the delegate is more restrictive than the
// parameter of the method (that is, the delegate accepts an
// instance of Derived, which can always be safely passed to
// a parameter of type Base), and the return type of MyMethod
// is more restrictive than the return type of Example (that
// is, the method returns an instance of Derived, which can
// always be safely cast to type Base).
let ex = Delegate.CreateDelegate(typeof<Example>, minfo) :?> Example

// Execute MyMethod using the delegate Example.
let b = Derived() |> ex.Invoke
Imports System.Reflection

' Define two classes to use in the demonstration, a base class and 
' a class that derives from it.
'
Public Class Base
End Class

Public Class Derived
    Inherits Base

    ' Define a Shared method to use in the demonstration. The method 
    ' takes an instance of Base and returns an instance of Derived.  
    ' For the purposes of the demonstration, it is not necessary for 
    ' the method to do anything useful. 
    '
    Public Shared Function MyMethod(ByVal arg As Base) As Derived
        Dim dummy As Base = arg
        Return New Derived()
    End Function

End Class

' Define a delegate that takes an instance of Derived and returns an
' instance of Base.
'
Public Delegate Function Example(ByVal arg As Derived) As Base

Module Test

    Sub Main()

        ' The binding flags needed to retrieve MyMethod.
        Dim flags As BindingFlags = _
            BindingFlags.Public Or BindingFlags.Static

        ' Get a MethodInfo that represents MyMethod.
        Dim minfo As MethodInfo = _
            GetType(Derived).GetMethod("MyMethod", flags)

        ' Demonstrate contravariance of parameter types and covariance
        ' of return types by using the delegate Example to represent
        ' MyMethod. The delegate binds to the method because the
        ' parameter of the delegate is more restrictive than the 
        ' parameter of the method (that is, the delegate accepts an
        ' instance of Derived, which can always be safely passed to
        ' a parameter of type Base), and the return type of MyMethod
        ' is more restrictive than the return type of Example (that
        ' is, the method returns an instance of Derived, which can
        ' always be safely cast to type Base). 
        '
        Dim ex As Example = CType( _
            [Delegate].CreateDelegate(GetType(Example), minfo), _
            Example _
        )

        ' Execute MyMethod using the delegate Example.
        '        
        Dim b As Base = ex(New Derived())
    End Sub
End Module

CreateDelegate(Type, Object, MethodInfo)CreateDelegate(Type, Object, MethodInfo, Boolean) 方法

这两个重载的功能相同,只是其中一个允许你指定在绑定失败时是否引发异常,而另一个则始终会引发异常。

委托类型和方法必须具有兼容的返回类型。 也就是说,method 的返回类型必须可以赋值给 type 的返回类型。

firstArgument,这些重载的第二个参数是委托表示的方法的第一个参数。 如果提供了 firstArgument,那么每次调用委托时它都会被传递给 method;此时可以说 firstArgument 绑定到了该委托,并且称该委托在其第一个参数上形成闭包。 如果 methodstaticShared 在 Visual Basic 中),则调用委托时提供的参数列表包括除第一个参数以外的所有参数;如果是 method 实例方法,则 firstArgument 传递给隐藏实例参数(在 this C# 中或 Me Visual Basic 中表示)。

如果 firstArgument 提供,则第一个参数 method 必须是引用类型,并且 firstArgument 必须与该类型兼容。

Important

如果 methodstaticShared 在 Visual Basic 中)及其第一个参数的类型 ObjectValueTypefirstArgument 可以是值类型。 在这种情况下 firstArgument 会自动装箱。 与在 C# 或 Visual Basic 函数调用中一样,对于任何其他参数都不会发生自动装箱。

如果 firstArgument 是 null 引用,并且 method 是实例方法,则结果取决于委托类型 typemethod 的签名。

  • 如果 type 的签名显式包含 method 的第一个隐藏参数,则称该委托表示一个开放实例方法。 调用委托时,参数列表中的第一个参数将传递给隐藏的 method实例参数。
  • 如果签名 methodtype 匹配(即所有参数类型都兼容),则称该委托在空引用上形成闭包。 调用委托就像对 null 实例调用实例方法一样,这不是一件特别有用的事情。

如果 firstArgument 为 null 引用且 method 是静态的,则结果取决于委托类型 typemethod 的签名。

  • 如果签名 methodtype 匹配(即所有参数类型都兼容),则表示委托表示开放静态方法。 这是静态方法最常见的情况。 在这种情况下,通过使用CreateDelegate(Type, MethodInfo) 方法重载可以获得更好的性能。
  • 如果 type 的签名以 method 的第二个参数开头,并且其余参数类型兼容,则称该委托在空引用上形成闭包。 调用委托时,向第一个参数 method传递空引用。

示例

下面的代码示例演示单个委托类型可以表示的所有方法:在实例方法上关闭、在实例方法上打开、在静态方法上打开,并通过静态方法关闭。

该代码示例定义了两个类CF,以及一个具有D类型参数的委托类型C。 这些类具有匹配的静态和实例方法 M1M3并且 M4C 也具有没有参数的实例方法 M2

名为 Example 的第三个类包含创建委托的代码。

  • 为类型 M1 和类型 C 的实例方法 F 创建委托;每个委托都在各自类型的一个实例上形成闭包。 类型为 M1 的方法 C 显示绑定实例和参数的 ID 属性。
  • 为类型 M2 的方法 C 创建一个委托。 这是一个开放实例委托,其中委托的参数表示实例方法上隐藏的第一个参数。 该方法没有其他参数。 它的调用方式就像是调用一个静态方法。
  • 为类型M3和类型C的静态方法F创建委托;这些是开放的静态委托。
  • 最后,为类型 M4 和类型 C 的静态方法 F 创建委托;每个方法都将声明类型作为其第一个参数,并提供该类型的一个实例,因此这些委托在其第一个参数上形成闭包。 类型为 M4 的方法 C 显示绑定实例和参数的 ID 属性。
using System;
using System.Reflection;

// Declare a delegate type. The object of this code example
// is to show all the methods this delegate can bind to.
//
public delegate void D(C1 c);

// Declare two sample classes, C1 and F. Class C1 has an ID
// property so instances can be identified.
//
public class C1
{
    private int id;
    public int ID => id;
    public C1(int id) => this.id = id;

    public void M1(C1 c)
    {
        Console.WriteLine("Instance method M1(C1 c) on C1:  this.id = {0}, c.ID = {1}",
            this.id, c.ID);
    }

    public void M2()
    {
        Console.WriteLine($"Instance method M2() on C1:  this.id = {this.id}");
    }

    public static void M3(C1 c)
    {
        Console.WriteLine($"Static method M3(C1 c) on C1:  c.ID = {c.ID}");
    }

    public static void M4(C1 c1, C1 c2)
    {
        Console.WriteLine("Static method M4(C1 c1, C1 c2) on C1:  c1.ID = {0}, c2.ID = {1}",
            c1.ID, c2.ID);
    }
}

public class F
{
    public void M1(C1 c)
    {
        Console.WriteLine($"Instance method M1(C1 c) on F:  c.ID = {c.ID}");
    }

    public static void M3(C1 c)
    {
        Console.WriteLine($"Static method M3(C1 c) on F:  c.ID = {c.ID}");
    }

    public static void M4(F f, C1 c)
    {
        Console.WriteLine($"Static method M4(F f, C1 c) on F:  c.ID = {c.ID}");
    }
}

public class Example
{
    public static void Main()
    {
        C1 c1 = new (42);
        C1 c2 = new (1491);
        F f1 = new ();

        D d;

        // Instance method with one argument of type C1.
        MethodInfo cmi1 = typeof(C1).GetMethod("M1");
        // Instance method with no arguments.
        MethodInfo cmi2 = typeof(C1).GetMethod("M2");
        // Static method with one argument of type C1.
        MethodInfo cmi3 = typeof(C1).GetMethod("M3");
        // Static method with two arguments of type C1.
        MethodInfo cmi4 = typeof(C1).GetMethod("M4");

        // Instance method with one argument of type C1.
        MethodInfo fmi1 = typeof(F).GetMethod("M1");
        // Static method with one argument of type C1.
        MethodInfo fmi3 = typeof(F).GetMethod("M3");
        // Static method with an argument of type F and an argument
        // of type C1.
        MethodInfo fmi4 = typeof(F).GetMethod("M4");

        Console.WriteLine("\nAn instance method on any type, with an argument of type C1.");
        // D can represent any instance method that exactly matches its
        // signature. Methods on C1 and F are shown here.
        //
        d = (D)Delegate.CreateDelegate(typeof(D), c1, cmi1);
        d(c2);
        d = (D)Delegate.CreateDelegate(typeof(D), f1, fmi1);
        d(c2);

        Console.WriteLine("\nAn instance method on C1 with no arguments.");
        // D can represent an instance method on C1 that has no arguments;
        // in this case, the argument of D represents the hidden first
        // argument of any instance method. The delegate acts like a
        // static method, and an instance of C1 must be passed each time
        // it is invoked.
        //
        d = (D)Delegate.CreateDelegate(typeof(D), null, cmi2);
        d(c1);

        Console.WriteLine("\nA static method on any type, with an argument of type C1.");
        // D can represent any static method with the same signature.
        // Methods on F and C1 are shown here.
        //
        d = (D)Delegate.CreateDelegate(typeof(D), null, cmi3);
        d(c1);
        d = (D)Delegate.CreateDelegate(typeof(D), null, fmi3);
        d(c1);

        Console.WriteLine("\nA static method on any type, with an argument of");
        Console.WriteLine("    that type and an argument of type C1.");
        // D can represent any static method with one argument of the
        // type the method belongs and a second argument of type C1.
        // In this case, the method is closed over the instance of
        // supplied for the its first argument, and acts like an instance
        // method. Methods on F and C1 are shown here.
        //
        d = (D)Delegate.CreateDelegate(typeof(D), c1, cmi4);
        d(c2);
        Delegate test =
            Delegate.CreateDelegate(typeof(D), f1, fmi4, false);

        // This final example specifies false for throwOnBindFailure
        // in the call to CreateDelegate, so the variable 'test'
        // contains Nothing if the method fails to bind (for
        // example, if fmi4 happened to represent a method of
        // some class other than F).
        //
        if (test != null)
        {
            d = (D)test;
            d(c2);
        }
    }
}

/* This code example produces the following output:

An instance method on any type, with an argument of type C1.
Instance method M1(C1 c) on C1:  this.id = 42, c.ID = 1491
Instance method M1(C1 c) on F:  c.ID = 1491

An instance method on C1 with no arguments.
Instance method M2() on C1:  this.id = 42

A static method on any type, with an argument of type C1.
Static method M3(C1 c) on C1:  c.ID = 42
Static method M3(C1 c) on F:  c.ID = 42

A static method on any type, with an argument of
    that type and an argument of type C1.
Static method M4(C1 c1, C1 c2) on C1:  c1.ID = 42, c2.ID = 1491
Static method M4(F f, C1 c) on F:  c.ID = 1491
*/
open System

// Declare two sample classes, C and F. Class C has an ID
// property so instances can be identified.
type C(id) =
    member _.ID = id 

    member _.M1(c: C) =
        printfn $"Instance method M1(C c) on C:  this.id = {id}, c.ID = {c.ID}"

    member _.M2() =
        printfn $"Instance method M2() on C:  this.id = {id}"

    static member M3(c: C) =
        printfn $"Static method M3(C c) on C:  c.ID = {c.ID}"

    static member M4(c1: C, c2: C) =
        printfn $"Static method M4(C c1, C c2) on C:  c1.ID = {c1.ID}, c2.ID = {c2.ID}"

// Declare a delegate type. The object of this code example
// is to show all the methods this delegate can bind to.
type D = delegate of C -> unit


type F() =
    member _.M1(c: C) =
        printfn $"Instance method M1(C c) on F:  c.ID = {c.ID}"

    member _.M3(c: C) =
        printfn $"Static method M3(C c) on F:  c.ID = {c.ID}"

    member _.M4(f: F, c: C) =
        printfn $"Static method M4(F f, C c) on F:  c.ID = {c.ID}"

[<EntryPoint>]
let main _ =
    let c1 = C 42
    let c2 = C 1491
    let f1 = F()

    // Instance method with one argument of type C.
    let cmi1 = typeof<C>.GetMethod "M1"
    // Instance method with no arguments.
    let cmi2 = typeof<C>.GetMethod "M2"
    // Static method with one argument of type C.
    let cmi3 = typeof<C>.GetMethod "M3"
    // Static method with two arguments of type C.
    let cmi4 = typeof<C>.GetMethod "M4"

    // Instance method with one argument of type C.
    let fmi1 = typeof<F>.GetMethod "M1"
    // Static method with one argument of type C.
    let fmi3 = typeof<F>.GetMethod "M3"
    // Static method with an argument of type F and an argument
    // of type C.
    let fmi4 = typeof<F>.GetMethod "M4"

    printfn "\nAn instance method on any type, with an argument of type C."
    // D can represent any instance method that exactly matches its
    // signature. Methods on C and F are shown here.
    let d = Delegate.CreateDelegate(typeof<D>, c1, cmi1) :?> D
    d.Invoke c2
    let d =  Delegate.CreateDelegate(typeof<D>, f1, fmi1) :?> D
    d.Invoke c2

    Console.WriteLine("\nAn instance method on C with no arguments.")
    // D can represent an instance method on C that has no arguments
    // in this case, the argument of D represents the hidden first
    // argument of any instance method. The delegate acts like a
    // static method, and an instance of C must be passed each time
    // it is invoked.
    let d = Delegate.CreateDelegate(typeof<D>, null, cmi2) :?> D
    d.Invoke c1

    printfn "\nA static method on any type, with an argument of type C."
    // D can represent any static method with the same signature.
    // Methods on F and C are shown here.
    let d = Delegate.CreateDelegate(typeof<D>, null, cmi3) :?> D
    d.Invoke c1
    let d = Delegate.CreateDelegate(typeof<D>, null, fmi3) :?> D
    d.Invoke c1

    printfn "\nA static method on any type, with an argument of"
    printfn "    that type and an argument of type C."
    // D can represent any static method with one argument of the
    // type the method belongs and a second argument of type C.
    // In this case, the method is closed over the instance of
    // supplied for the its first argument, and acts like an instance
    // method. Methods on F and C are shown here.
    let d = Delegate.CreateDelegate(typeof<D>, c1, cmi4) :?> D
    d.Invoke c2
    let test =
        Delegate.CreateDelegate(typeof<D>, f1, fmi4, false)

    // This final example specifies false for throwOnBindFailure
    // in the call to CreateDelegate, so the variable 'test'
    // contains Nothing if the method fails to bind (for
    // example, if fmi4 happened to represent a method of
    // some class other than F).
    match test with
    | :? D as d ->
        d.Invoke c2
    | _ -> ()
    0

// This code example produces the following output:
//     An instance method on any type, with an argument of type C.
//     Instance method M1(C c) on C:  this.id = 42, c.ID = 1491
//     Instance method M1(C c) on F:  c.ID = 1491
//    
//     An instance method on C with no arguments.
//     Instance method M2() on C:  this.id = 42
//    
//     A static method on any type, with an argument of type C.
//     Static method M3(C c) on C:  c.ID = 42
//     Static method M3(C c) on F:  c.ID = 42
//    
//     A static method on any type, with an argument of
//         that type and an argument of type C.
//     Static method M4(C c1, C c2) on C:  c1.ID = 42, c2.ID = 1491
//     Static method M4(F f, C c) on F:  c.ID = 1491
Imports System.Reflection
Imports System.Security.Permissions

' Declare a delegate type. The object of this code example
' is to show all the methods this delegate can bind to.
'
Public Delegate Sub D(ByVal c As C) 

' Declare two sample classes, C and F. Class C has an ID
' property so instances can be identified.
'
Public Class C

    Private _id As Integer

    Public ReadOnly Property ID() As Integer 
        Get
            Return _id
        End Get
    End Property

    Public Sub New(ByVal newId As Integer) 
        Me._id = newId
    End Sub
    
    Public Sub M1(ByVal c As C) 
        Console.WriteLine("Instance method M1(c As C) on C:  this.id = {0}, c.ID = {1}", _
            Me.id, c.ID)
    End Sub
    
    Public Sub M2() 
        Console.WriteLine("Instance method M2() on C:  this.id = {0}", Me.id)
    End Sub
    
    Public Shared Sub M3(ByVal c As C) 
        Console.WriteLine("Shared method M3(c As C) on C:  c.ID = {0}", c.ID)
    End Sub
    
    Public Shared Sub M4(ByVal c1 As C, ByVal c2 As C) 
        Console.WriteLine("Shared method M4(c1 As C, c2 As C) on C:  c1.ID = {0}, c2.ID = {1}", _
            c1.ID, c2.ID)
    End Sub
End Class


Public Class F
    
    Public Sub M1(ByVal c As C) 
        Console.WriteLine("Instance method M1(c As C) on F:  c.ID = {0}", c.ID)
    End Sub
    
    Public Shared Sub M3(ByVal c As C) 
        Console.WriteLine("Shared method M3(c As C) on F:  c.ID = {0}", c.ID)
    End Sub
    
    Public Shared Sub M4(ByVal f As F, ByVal c As C) 
        Console.WriteLine("Shared method M4(f As F, c As C) on F:  c.ID = {0}", c.ID)
    End Sub
End Class

Public Class Example5

    Public Shared Sub Main()

        Dim c1 As New C(42)
        Dim c2 As New C(1491)
        Dim f1 As New F()

        Dim d As D

        ' Instance method with one argument of type C.
        Dim cmi1 As MethodInfo = GetType(C).GetMethod("M1")
        ' Instance method with no arguments.
        Dim cmi2 As MethodInfo = GetType(C).GetMethod("M2")
        ' Shared method with one argument of type C.
        Dim cmi3 As MethodInfo = GetType(C).GetMethod("M3")
        ' Shared method with two arguments of type C.
        Dim cmi4 As MethodInfo = GetType(C).GetMethod("M4")

        ' Instance method with one argument of type C.
        Dim fmi1 As MethodInfo = GetType(F).GetMethod("M1")
        ' Shared method with one argument of type C.
        Dim fmi3 As MethodInfo = GetType(F).GetMethod("M3")
        ' Shared method with an argument of type F and an 
        ' argument of type C.
        Dim fmi4 As MethodInfo = GetType(F).GetMethod("M4")

        Console.WriteLine(vbLf & "An instance method on any type, with an argument of type C.")
        ' D can represent any instance method that exactly matches its
        ' signature. Methods on C and F are shown here.
        '
        d = CType([Delegate].CreateDelegate(GetType(D), c1, cmi1), D)
        d(c2)
        d = CType([Delegate].CreateDelegate(GetType(D), f1, fmi1), D)
        d(c2)

        Console.WriteLine(vbLf & "An instance method on C with no arguments.")
        ' D can represent an instance method on C that has no arguments;
        ' in this case, the argument of D represents the hidden first
        ' argument of any instance method. The delegate acts like a 
        ' Shared method, and an instance of C must be passed each time
        ' it is invoked.
        '
        d = CType([Delegate].CreateDelegate(GetType(D), Nothing, cmi2), D)
        d(c1)

        Console.WriteLine(vbLf & "A Shared method on any type, with an argument of type C.")
        ' D can represent any Shared method with the same signature.
        ' Methods on F and C are shown here.
        '
        d = CType([Delegate].CreateDelegate(GetType(D), Nothing, cmi3), D)
        d(c1)
        d = CType([Delegate].CreateDelegate(GetType(D), Nothing, fmi3), D)
        d(c1)

        Console.WriteLine(vbLf & "A Shared method on any type, with an argument of")
        Console.WriteLine("    that type and an argument of type C.")
        ' D can represent any Shared method with one argument of the
        ' type the method belongs and a second argument of type C.
        ' In this case, the method is closed over the instance of
        ' supplied for the its first argument, and acts like an instance
        ' method. Methods on F and C are shown here.
        '
        d = CType([Delegate].CreateDelegate(GetType(D), c1, cmi4), D)
        d(c2)
        Dim test As [Delegate] =
            [Delegate].CreateDelegate(GetType(D), f1, fmi4, False)

        ' This final example specifies False for throwOnBindFailure 
        ' in the call to CreateDelegate, so the variable 'test'
        ' contains Nothing if the method fails to bind (for 
        ' example, if fmi4 happened to represent a method of  
        ' some class other than F).
        '
        If test IsNot Nothing Then
            d = CType(test, D)
            d(c2)
        End If

    End Sub
End Class

' This code example produces the following output:
'
'An instance method on any type, with an argument of type C.
'Instance method M1(c As C) on C:  this.id = 42, c.ID = 1491
'Instance method M1(c As C) on F:  c.ID = 1491
'
'An instance method on C with no arguments.
'Instance method M2() on C:  this.id = 42
'
'A Shared method on any type, with an argument of type C.
'Shared method M3(c As C) on C:  c.ID = 42
'Shared method M3(c As C) on F:  c.ID = 42
'
'A Shared method on any type, with an argument of
'    that type and an argument of type C.
'Shared method M4(c1 As C, c2 As C) on C:  c1.ID = 42, c2.ID = 1491
'Shared method M4(f As F, c As C) on F:  c.ID = 1491
'

兼容的参数类型和返回类型

使用此方法重载创建的委托的参数类型和返回类型必须与委托表示的方法的参数类型和返回类型兼容;类型不必完全匹配。

如果委托的类型比方法参数的类型更严格,则委托参数的参数与方法的相应参数兼容,因为这样可以保证传递给委托的参数可以安全地传递给该方法。

同样,如果方法的返回类型比委托的返回类型更严格,则委托的返回类型与方法的返回类型兼容,因为这样可以保证方法的返回值可以安全地强制转换为委托的返回类型。

例如,具有类型参数 Hashtable 和返回类型 Object 的委托可以表示具有类型参数 Object 和返回值类型 Hashtable 的方法。

确定委托可以代表的方法

考虑CreateDelegate(Type, Object, MethodInfo)重载提供的灵活性的一种有用方式是,任何给定的委托都可以表示方法签名和方法类型(静态与实例)的四种不同组合。 考虑一个具有类型为 D 的参数的委托类型 C。 下面描述了方法 D 能够代表的内容,忽略返回类型,因为它在所有情况下都必须匹配。

  • D 可以表示具有一个类型为 C 参数的任何实例方法,而不考虑该实例方法属于哪种类型。 当调用 CreateDelegate 时,firstArgumentmethod 所属类型的一个实例,并且称由此生成的委托在该实例上形成闭包。 (简单来说,如果 D 是一个空引用,firstArgument 也可以在空引用上形成闭包。)

  • D 可以表示没有参数的 C 实例方法。 当调用 CreateDelegate 时,firstArgument 是空引用。 生成的委托表示一个开放的实例方法,并且每次调用时都必须提供一个C实例。

  • D 可以表示采用一个类型的 C参数的静态方法,并且该方法可以属于任何类型。 当调用 CreateDelegate 时,firstArgument 是空引用。 生成的委托表示一个打开的静态方法,每次调用它时都必须提供一个实例 C

  • D可以表示属于F类型的静态方法,并且具有两个参数,分别属于F类型和C类型。 调用CreateDelegate 时,firstArgumentF的一个实例。 生成的委托表示在 F 的该实例上形成闭包的静态方法。 请注意,在相同类型的情况下FC,静态方法具有该类型的两个参数。 (在这种情况下,如果 D 是一个空引用,则 firstArgument 在空引用上形成闭包。)

注解

调用此方法重载等效于调用CreateDelegate(Type, Object, MethodInfo, Boolean)方法重载并为其true指定 throwOnBindFailure 。 这两个重载提供了创建委托的最灵活方法。 可以使用它们为静态方法或实例方法创建委托,还可以选择指定第一个参数。

注释

如果未提供第一个参数,请使用 CreateDelegate(Type, MethodInfo) 方法重载来提高性能。

CreateDelegate 方法会创建指定类型的委托。

CreateDelegate(Type, MethodInfo) 方法

此方法重载等效于调用CreateDelegate(Type, MethodInfo, Boolean)的重载,并为true指定throwOnBindFailure

另请参阅

适用于

CreateDelegate(Type, MethodInfo)

Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs

创建指定类型的委托来表示指定的方法。

public:
 static Delegate ^ CreateDelegate(Type ^ type, System::Reflection::MethodInfo ^ method);
public static Delegate CreateDelegate(Type type, System.Reflection.MethodInfo method);
static member CreateDelegate : Type * System.Reflection.MethodInfo -> Delegate
Public Shared Function CreateDelegate (type As Type, method As MethodInfo) As Delegate

参数

type
Type

Type要创建的委托。

method
MethodInfo

MethodInfo描述委托要表示的静态或实例方法。

返回

表示指定方法的指定类型的委托。

例外

typenull

-或-

methodnull

type 不继承 MulticastDelegate

-或-

type不是 .RuntimeType 请参阅 反射中的运行时类型

-或-

method 无法绑定。

-或-

method不是 .RuntimeMethodInfo 请参阅 反射中的运行时类型

Invoke找不到方法type

调用方没有访问 method所需的权限。

示例

本部分包含两个代码示例。 第一个示例演示了可以使用此方法重载创建的两种类型的委托:在实例方法上打开并打开静态方法。

第二个代码示例演示了兼容的参数类型和返回类型。

示例 1

以下代码示例演示了使用 CreateDelegate 方法的这个重载来创建委托的两种方式。

注释

CreateDelegate 方法有两个重载,它们指定一个 MethodInfo 但没有指定第一个参数;它们的功能相同,只是其中一个允许你指定在绑定失败时是否引发异常,而另一个则始终会引发异常。 此代码示例使用这两个重载。

该示例声明类C,带有静态方法M2和实例方法M1,以及两种委托类型:D1 使用类的实例C和一个字符串,D2 使用一个字符串。

第二个名为Example的类包含用于创建委托的代码。

  • 为实例方法 D1 创建了一个类型为 M1 的委托,代表一个开放实例方法。 调用委托时必须传递一个实例。
  • 为静态方法 D2 创建类型 M2 的委托,该委托表示开放的静态方法。
using System;
using System.Reflection;

// Declare three delegate types for demonstrating the combinations
// of static versus instance methods and open versus closed
// delegates.
//
public delegate void D1(C c, string s);
public delegate void D2(string s);
public delegate void D3();

// A sample class with an instance method and a static method.
//
public class C
{
    private int id;
    public C(int id) { this.id = id; }

    public void M1(string s) =>
        Console.WriteLine($"Instance method M1 on C:  id = {this.id}, s = {s}");

    public static void M2(string s)
    {
        Console.WriteLine($"Static method M2 on C:  s = {s}");
    }
}

public class Example2
{
    public static void Main()
    {
        C c1 = new C(42);

        // Get a MethodInfo for each method.
        //
        MethodInfo mi1 = typeof(C).GetMethod("M1",
            BindingFlags.Public | BindingFlags.Instance);
        MethodInfo mi2 = typeof(C).GetMethod("M2",
            BindingFlags.Public | BindingFlags.Static);

        D1 d1;
        D2 d2;
        D3 d3;

        Console.WriteLine("\nAn instance method closed over C.");
        // In this case, the delegate and the
        // method must have the same list of argument types; use
        // delegate type D2 with instance method M1.
        //
        Delegate test =
            Delegate.CreateDelegate(typeof(D2), c1, mi1, false);

        // Because false was specified for throwOnBindFailure
        // in the call to CreateDelegate, the variable 'test'
        // contains null if the method fails to bind (for
        // example, if mi1 happened to represent a method of
        // some class other than C).
        //
        if (test != null)
        {
            d2 = (D2)test;

            // The same instance of C is used every time the
            // delegate is invoked.
            d2("Hello, World!");
            d2("Hi, Mom!");
        }

        Console.WriteLine("\nAn open instance method.");
        // In this case, the delegate has one more
        // argument than the instance method; this argument comes
        // at the beginning, and represents the hidden instance
        // argument of the instance method. Use delegate type D1
        // with instance method M1.
        //
        d1 = (D1)Delegate.CreateDelegate(typeof(D1), null, mi1);

        // An instance of C must be passed in each time the
        // delegate is invoked.
        //
        d1(c1, "Hello, World!");
        d1(new C(5280), "Hi, Mom!");

        Console.WriteLine("\nAn open static method.");
        // In this case, the delegate and the method must
        // have the same list of argument types; use delegate type
        // D2 with static method M2.
        //
        d2 = (D2)Delegate.CreateDelegate(typeof(D2), null, mi2);

        // No instances of C are involved, because this is a static
        // method.
        //
        d2("Hello, World!");
        d2("Hi, Mom!");

        Console.WriteLine("\nA static method closed over the first argument (String).");
        // The delegate must omit the first argument of the method.
        // A string is passed as the firstArgument parameter, and
        // the delegate is bound to this string. Use delegate type
        // D3 with static method M2.
        //
        d3 = (D3)Delegate.CreateDelegate(typeof(D3),
            "Hello, World!", mi2);

        // Each time the delegate is invoked, the same string is
        // used.
        d3();
    }
}

/* This code example produces the following output:

An instance method closed over C.
Instance method M1 on C:  id = 42, s = Hello, World!
Instance method M1 on C:  id = 42, s = Hi, Mom!

An open instance method.
Instance method M1 on C:  id = 42, s = Hello, World!
Instance method M1 on C:  id = 5280, s = Hi, Mom!

An open static method.
Static method M2 on C:  s = Hello, World!
Static method M2 on C:  s = Hi, Mom!

A static method closed over the first argument (String).
Static method M2 on C:  s = Hello, World!
 */
open System
open System.Reflection

// A sample class with an instance method and a static method.
type C(id) =
    member _.M1(s) =
        printfn $"Instance method M1 on C:  id = %i{id}, s = %s{s}"

    static member M2(s) =
        printfn $"Static method M2 on C:  s = %s{s}"
    
// Declare three delegate types for demonstrating the combinations
// of static versus instance methods and open versus closed
// delegates.
type D1 = delegate of C * string -> unit
type D2 = delegate of string -> unit
type D3 = delegate of unit -> unit

let c1 = C 42

// Get a MethodInfo for each method.
//
let mi1 = typeof<C>.GetMethod("M1", BindingFlags.Public ||| BindingFlags.Instance)
let mi2 = typeof<C>.GetMethod("M2", BindingFlags.Public ||| BindingFlags.Static)

printfn "\nAn instance method closed over C."

// In this case, the delegate and the
// method must have the same list of argument types use
// delegate type D2 with instance method M1.
let test = Delegate.CreateDelegate(typeof<D2>, c1, mi1, false)

// Because false was specified for throwOnBindFailure
// in the call to CreateDelegate, the variable 'test'
// contains null if the method fails to bind (for
// example, if mi1 happened to represent a method of
// some class other than C).
if test <> null then
    let d2 = test :?> D2

    // The same instance of C is used every time the
    // delegate is invoked.
    d2.Invoke "Hello, World!"
    d2.Invoke "Hi, Mom!"

printfn "\nAn open instance method."

// In this case, the delegate has one more
// argument than the instance method this argument comes
// at the beginning, and represents the hidden instance
// argument of the instance method. Use delegate type D1
// with instance method M1.
let d1 = Delegate.CreateDelegate(typeof<D1>, null, mi1) :?> D1

// An instance of C must be passed in each time the
// delegate is invoked.
d1.Invoke(c1, "Hello, World!")
d1.Invoke(C 5280, "Hi, Mom!")

printfn "\nAn open static method."
// In this case, the delegate and the method must
// have the same list of argument types use delegate type
// D2 with static method M2.
let d2 = Delegate.CreateDelegate(typeof<D2>, null, mi2) :?> D2

// No instances of C are involved, because this is a static
// method.
d2.Invoke "Hello, World!"
d2.Invoke "Hi, Mom!"

printfn "\nA static method closed over the first argument (String)."
// The delegate must omit the first argument of the method.
// A string is passed as the firstArgument parameter, and
// the delegate is bound to this string. Use delegate type
// D3 with static method M2.
let d3 = Delegate.CreateDelegate(typeof<D3>, "Hello, World!", mi2) :?> D3

// Each time the delegate is invoked, the same string is used.
d3.Invoke()

// This code example produces the following output:
//     An instance method closed over C.
//     Instance method M1 on C:  id = 42, s = Hello, World!
//     Instance method M1 on C:  id = 42, s = Hi, Mom!
//     
//     An open instance method.
//     Instance method M1 on C:  id = 42, s = Hello, World!
//     Instance method M1 on C:  id = 5280, s = Hi, Mom!
//     
//     An open static method.
//     Static method M2 on C:  s = Hello, World!
//     Static method M2 on C:  s = Hi, Mom!
//     
//     A static method closed over the first argument (String).
//     Static method M2 on C:  s = Hello, World!
Imports System.Reflection
Imports System.Security.Permissions

' Declare three delegate types for demonstrating the combinations
' of Shared versus instance methods and open versus closed
' delegates.
'
Public Delegate Sub D1(ByVal c As C2, ByVal s As String)
Public Delegate Sub D2(ByVal s As String)
Public Delegate Sub D3()

' A sample class with an instance method and a Shared method.
'
Public Class C2
    Private id As Integer
    Public Sub New(ByVal id As Integer)
        Me.id = id
    End Sub

    Public Sub M1(ByVal s As String)
        Console.WriteLine("Instance method M1 on C2:  id = {0}, s = {1}",
            Me.id, s)
    End Sub

    Public Shared Sub M2(ByVal s As String)
        Console.WriteLine("Shared method M2 on C2:  s = {0}", s)
    End Sub
End Class

Public Class Example2

    Public Shared Sub Main()

        Dim c1 As New C2(42)

        ' Get a MethodInfo for each method.
        '
        Dim mi1 As MethodInfo = GetType(C2).GetMethod("M1",
            BindingFlags.Public Or BindingFlags.Instance)
        Dim mi2 As MethodInfo = GetType(C2).GetMethod("M2",
            BindingFlags.Public Or BindingFlags.Static)

        Dim d1 As D1
        Dim d2 As D2
        Dim d3 As D3


        Console.WriteLine(vbLf & "An instance method closed over C2.")
        ' In this case, the delegate and the
        ' method must have the same list of argument types; use
        ' delegate type D2 with instance method M1.
        '
        Dim test As [Delegate] =
            [Delegate].CreateDelegate(GetType(D2), c1, mi1, False)

        ' Because False was specified for throwOnBindFailure 
        ' in the call to CreateDelegate, the variable 'test'
        ' contains Nothing if the method fails to bind (for 
        ' example, if mi1 happened to represent a method of 
        ' some class other than C2).
        '
        If test IsNot Nothing Then
            d2 = CType(test, D2)

            ' The same instance of C2 is used every time the
            ' delegate is invoked.
            d2("Hello, World!")
            d2("Hi, Mom!")
        End If


        Console.WriteLine(vbLf & "An open instance method.")
        ' In this case, the delegate has one more 
        ' argument than the instance method; this argument comes
        ' at the beginning, and represents the hidden instance
        ' argument of the instance method. Use delegate type D1
        ' with instance method M1.
        '
        d1 = CType([Delegate].CreateDelegate(GetType(D1), Nothing, mi1), D1)

        ' An instance of C2 must be passed in each time the 
        ' delegate is invoked.
        '
        d1(c1, "Hello, World!")
        d1(New C2(5280), "Hi, Mom!")


        Console.WriteLine(vbLf & "An open Shared method.")
        ' In this case, the delegate and the method must 
        ' have the same list of argument types; use delegate type
        ' D2 with Shared method M2.
        '
        d2 = CType([Delegate].CreateDelegate(GetType(D2), Nothing, mi2), D2)

        ' No instances of C2 are involved, because this is a Shared
        ' method. 
        '
        d2("Hello, World!")
        d2("Hi, Mom!")


        Console.WriteLine(vbLf & "A Shared method closed over the first argument (String).")
        ' The delegate must omit the first argument of the method.
        ' A string is passed as the firstArgument parameter, and 
        ' the delegate is bound to this string. Use delegate type 
        ' D3 with Shared method M2. 
        '
        d3 = CType([Delegate].CreateDelegate(GetType(D3), "Hello, World!", mi2), D3)

        ' Each time the delegate is invoked, the same string is
        ' used.
        d3()

    End Sub
End Class

' This code example produces the following output:
'
'An instance method closed over C2.
'Instance method M1 on C2:  id = 42, s = Hello, World!
'Instance method M1 on C2:  id = 42, s = Hi, Mom!
'
'An open instance method.
'Instance method M1 on C2:  id = 42, s = Hello, World!
'Instance method M1 on C2:  id = 5280, s = Hi, Mom!
'
'An open Shared method.
'Shared method M2 on C2:  s = Hello, World!
'Shared method M2 on C2:  s = Hi, Mom!
'
'A Shared method closed over the first argument (String).
'Shared method M2 on C2:  s = Hello, World!
'

示例 2

下面的代码示例演示参数类型和返回类型的兼容性。

该代码示例定义了一个基类,命名为 Base,以及一个命名为 Derived 的类继承自 Base。 派生类有一个名为 staticShared(在 Visual Basic 中为 MyMethod)方法,该方法有一个类型为 Base 的参数,返回类型为 Derived。 该代码示例还定义了一个名为 Example 的委托,该委托具有一个类型为 Derived 的参数和一个类型为 Base 的返回值。

代码示例演示如何使用命名 Example 的委托来表示方法 MyMethod。 该方法可以绑定到委托,原因如下:

  • 委托()的参数类型比 (DerivedMyMethod) 的参数类型Base更严格,以便始终安全地将委托的参数传递给 MyMethod
  • MyMethod (Derived) 的返回类型比委托 (Base) 的参数类型更严格,因此将方法的返回类型强制转换为委托的返回类型始终是安全的。

该代码示例不生成任何输出。

using System;
using System.Reflection;

// Define two classes to use in the demonstration, a base class and
// a class that derives from it.
//
public class Base { }

public class Derived : Base
{
    // Define a static method to use in the demonstration. The method
    // takes an instance of Base and returns an instance of Derived.
    // For the purposes of the demonstration, it is not necessary for
    // the method to do anything useful.
    //
    public static Derived MyMethod(Base arg)
    {
        Base dummy = arg;
        return new Derived();
    }
}

// Define a delegate that takes an instance of Derived and returns an
// instance of Base.
//
public delegate Base Example5(Derived arg);

class Test
{
    public static void Main()
    {
        // The binding flags needed to retrieve MyMethod.
        BindingFlags flags = BindingFlags.Public | BindingFlags.Static;

        // Get a MethodInfo that represents MyMethod.
        MethodInfo minfo = typeof(Derived).GetMethod("MyMethod", flags);

        // Demonstrate contravariance of parameter types and covariance
        // of return types by using the delegate Example5 to represent
        // MyMethod. The delegate binds to the method because the
        // parameter of the delegate is more restrictive than the
        // parameter of the method (that is, the delegate accepts an
        // instance of Derived, which can always be safely passed to
        // a parameter of type Base), and the return type of MyMethod
        // is more restrictive than the return type of Example5 (that
        // is, the method returns an instance of Derived, which can
        // always be safely cast to type Base).
        //
        Example5 ex =
            (Example5)Delegate.CreateDelegate(typeof(Example5), minfo);

        // Execute MyMethod using the delegate Example5.
        //
        Base b = ex(new Derived());
    }
}
open System
open System.Reflection

// Define two classes to use in the demonstration, a base class and
// a class that derives from it.
type Base() = class end

type Derived() =
    inherit Base()

    // Define a static method to use in the demonstration. The method
    // takes an instance of Base and returns an instance of Derived.
    // For the purposes of the demonstration, it is not necessary for
    // the method to do anything useful.
    static member MyMethod(arg: Base) =
        Derived()

// Define a delegate that takes an instance of Derived and returns an
// instance of Base.
type Example = delegate of Derived -> Base

// The binding flags needed to retrieve MyMethod.
let flags = BindingFlags.Public ||| BindingFlags.Static

// Get a MethodInfo that represents MyMethod.
let minfo = typeof<Derived>.GetMethod("MyMethod", flags)

// Demonstrate contravariance of parameter types and covariance
// of return types by using the delegate Example to represent
// MyMethod. The delegate binds to the method because the
// parameter of the delegate is more restrictive than the
// parameter of the method (that is, the delegate accepts an
// instance of Derived, which can always be safely passed to
// a parameter of type Base), and the return type of MyMethod
// is more restrictive than the return type of Example (that
// is, the method returns an instance of Derived, which can
// always be safely cast to type Base).
let ex = Delegate.CreateDelegate(typeof<Example>, minfo) :?> Example

// Execute MyMethod using the delegate Example.
let b = Derived() |> ex.Invoke
Imports System.Reflection

' Define two classes to use in the demonstration, a base class and 
' a class that derives from it.
'
Public Class Base
End Class

Public Class Derived
    Inherits Base

    ' Define a Shared method to use in the demonstration. The method 
    ' takes an instance of Base and returns an instance of Derived.  
    ' For the purposes of the demonstration, it is not necessary for 
    ' the method to do anything useful. 
    '
    Public Shared Function MyMethod(ByVal arg As Base) As Derived
        Dim dummy As Base = arg
        Return New Derived()
    End Function

End Class

' Define a delegate that takes an instance of Derived and returns an
' instance of Base.
'
Public Delegate Function Example(ByVal arg As Derived) As Base

Module Test

    Sub Main()

        ' The binding flags needed to retrieve MyMethod.
        Dim flags As BindingFlags = _
            BindingFlags.Public Or BindingFlags.Static

        ' Get a MethodInfo that represents MyMethod.
        Dim minfo As MethodInfo = _
            GetType(Derived).GetMethod("MyMethod", flags)

        ' Demonstrate contravariance of parameter types and covariance
        ' of return types by using the delegate Example to represent
        ' MyMethod. The delegate binds to the method because the
        ' parameter of the delegate is more restrictive than the 
        ' parameter of the method (that is, the delegate accepts an
        ' instance of Derived, which can always be safely passed to
        ' a parameter of type Base), and the return type of MyMethod
        ' is more restrictive than the return type of Example (that
        ' is, the method returns an instance of Derived, which can
        ' always be safely cast to type Base). 
        '
        Dim ex As Example = CType( _
            [Delegate].CreateDelegate(GetType(Example), minfo), _
            Example _
        )

        ' Execute MyMethod using the delegate Example.
        '        
        Dim b As Base = ex(New Derived())
    End Sub
End Module

CreateDelegate(Type, Object, MethodInfo)CreateDelegate(Type, Object, MethodInfo, Boolean) 方法

这两个重载的功能相同,只是其中一个允许你指定在绑定失败时是否引发异常,而另一个则始终会引发异常。

委托类型和方法必须具有兼容的返回类型。 也就是说,method 的返回类型必须可以赋值给 type 的返回类型。

firstArgument,这些重载的第二个参数是委托表示的方法的第一个参数。 如果提供了 firstArgument,那么每次调用委托时它都会被传递给 method;此时可以说 firstArgument 绑定到了该委托,并且称该委托在其第一个参数上形成闭包。 如果 methodstaticShared 在 Visual Basic 中),则调用委托时提供的参数列表包括除第一个参数以外的所有参数;如果是 method 实例方法,则 firstArgument 传递给隐藏实例参数(在 this C# 中或 Me Visual Basic 中表示)。

如果 firstArgument 提供,则第一个参数 method 必须是引用类型,并且 firstArgument 必须与该类型兼容。

Important

如果 methodstaticShared 在 Visual Basic 中)及其第一个参数的类型 ObjectValueTypefirstArgument 可以是值类型。 在这种情况下 firstArgument 会自动装箱。 与在 C# 或 Visual Basic 函数调用中一样,对于任何其他参数都不会发生自动装箱。

如果 firstArgument 是 null 引用,并且 method 是实例方法,则结果取决于委托类型 typemethod 的签名。

  • 如果 type 的签名显式包含 method 的第一个隐藏参数,则称该委托表示一个开放实例方法。 调用委托时,参数列表中的第一个参数将传递给隐藏的 method实例参数。
  • 如果签名 methodtype 匹配(即所有参数类型都兼容),则称该委托在空引用上形成闭包。 调用委托就像对 null 实例调用实例方法一样,这不是一件特别有用的事情。

如果 firstArgument 为 null 引用且 method 是静态的,则结果取决于委托类型 typemethod 的签名。

  • 如果签名 methodtype 匹配(即所有参数类型都兼容),则表示委托表示开放静态方法。 这是静态方法最常见的情况。 在这种情况下,通过使用CreateDelegate(Type, MethodInfo) 方法重载可以获得更好的性能。
  • 如果 type 的签名以 method 的第二个参数开头,并且其余参数类型兼容,则称该委托在空引用上形成闭包。 调用委托时,向第一个参数 method传递空引用。

示例

下面的代码示例演示单个委托类型可以表示的所有方法:在实例方法上关闭、在实例方法上打开、在静态方法上打开,并通过静态方法关闭。

该代码示例定义了两个类CF,以及一个具有D类型参数的委托类型C。 这些类具有匹配的静态和实例方法 M1M3并且 M4C 也具有没有参数的实例方法 M2

名为 Example 的第三个类包含创建委托的代码。

  • 为类型 M1 和类型 C 的实例方法 F 创建委托;每个委托都在各自类型的一个实例上形成闭包。 类型为 M1 的方法 C 显示绑定实例和参数的 ID 属性。
  • 为类型 M2 的方法 C 创建一个委托。 这是一个开放实例委托,其中委托的参数表示实例方法上隐藏的第一个参数。 该方法没有其他参数。 它的调用方式就像是调用一个静态方法。
  • 为类型M3和类型C的静态方法F创建委托;这些是开放的静态委托。
  • 最后,为类型 M4 和类型 C 的静态方法 F 创建委托;每个方法都将声明类型作为其第一个参数,并提供该类型的一个实例,因此这些委托在其第一个参数上形成闭包。 类型为 M4 的方法 C 显示绑定实例和参数的 ID 属性。
using System;
using System.Reflection;

// Declare a delegate type. The object of this code example
// is to show all the methods this delegate can bind to.
//
public delegate void D(C1 c);

// Declare two sample classes, C1 and F. Class C1 has an ID
// property so instances can be identified.
//
public class C1
{
    private int id;
    public int ID => id;
    public C1(int id) => this.id = id;

    public void M1(C1 c)
    {
        Console.WriteLine("Instance method M1(C1 c) on C1:  this.id = {0}, c.ID = {1}",
            this.id, c.ID);
    }

    public void M2()
    {
        Console.WriteLine($"Instance method M2() on C1:  this.id = {this.id}");
    }

    public static void M3(C1 c)
    {
        Console.WriteLine($"Static method M3(C1 c) on C1:  c.ID = {c.ID}");
    }

    public static void M4(C1 c1, C1 c2)
    {
        Console.WriteLine("Static method M4(C1 c1, C1 c2) on C1:  c1.ID = {0}, c2.ID = {1}",
            c1.ID, c2.ID);
    }
}

public class F
{
    public void M1(C1 c)
    {
        Console.WriteLine($"Instance method M1(C1 c) on F:  c.ID = {c.ID}");
    }

    public static void M3(C1 c)
    {
        Console.WriteLine($"Static method M3(C1 c) on F:  c.ID = {c.ID}");
    }

    public static void M4(F f, C1 c)
    {
        Console.WriteLine($"Static method M4(F f, C1 c) on F:  c.ID = {c.ID}");
    }
}

public class Example
{
    public static void Main()
    {
        C1 c1 = new (42);
        C1 c2 = new (1491);
        F f1 = new ();

        D d;

        // Instance method with one argument of type C1.
        MethodInfo cmi1 = typeof(C1).GetMethod("M1");
        // Instance method with no arguments.
        MethodInfo cmi2 = typeof(C1).GetMethod("M2");
        // Static method with one argument of type C1.
        MethodInfo cmi3 = typeof(C1).GetMethod("M3");
        // Static method with two arguments of type C1.
        MethodInfo cmi4 = typeof(C1).GetMethod("M4");

        // Instance method with one argument of type C1.
        MethodInfo fmi1 = typeof(F).GetMethod("M1");
        // Static method with one argument of type C1.
        MethodInfo fmi3 = typeof(F).GetMethod("M3");
        // Static method with an argument of type F and an argument
        // of type C1.
        MethodInfo fmi4 = typeof(F).GetMethod("M4");

        Console.WriteLine("\nAn instance method on any type, with an argument of type C1.");
        // D can represent any instance method that exactly matches its
        // signature. Methods on C1 and F are shown here.
        //
        d = (D)Delegate.CreateDelegate(typeof(D), c1, cmi1);
        d(c2);
        d = (D)Delegate.CreateDelegate(typeof(D), f1, fmi1);
        d(c2);

        Console.WriteLine("\nAn instance method on C1 with no arguments.");
        // D can represent an instance method on C1 that has no arguments;
        // in this case, the argument of D represents the hidden first
        // argument of any instance method. The delegate acts like a
        // static method, and an instance of C1 must be passed each time
        // it is invoked.
        //
        d = (D)Delegate.CreateDelegate(typeof(D), null, cmi2);
        d(c1);

        Console.WriteLine("\nA static method on any type, with an argument of type C1.");
        // D can represent any static method with the same signature.
        // Methods on F and C1 are shown here.
        //
        d = (D)Delegate.CreateDelegate(typeof(D), null, cmi3);
        d(c1);
        d = (D)Delegate.CreateDelegate(typeof(D), null, fmi3);
        d(c1);

        Console.WriteLine("\nA static method on any type, with an argument of");
        Console.WriteLine("    that type and an argument of type C1.");
        // D can represent any static method with one argument of the
        // type the method belongs and a second argument of type C1.
        // In this case, the method is closed over the instance of
        // supplied for the its first argument, and acts like an instance
        // method. Methods on F and C1 are shown here.
        //
        d = (D)Delegate.CreateDelegate(typeof(D), c1, cmi4);
        d(c2);
        Delegate test =
            Delegate.CreateDelegate(typeof(D), f1, fmi4, false);

        // This final example specifies false for throwOnBindFailure
        // in the call to CreateDelegate, so the variable 'test'
        // contains Nothing if the method fails to bind (for
        // example, if fmi4 happened to represent a method of
        // some class other than F).
        //
        if (test != null)
        {
            d = (D)test;
            d(c2);
        }
    }
}

/* This code example produces the following output:

An instance method on any type, with an argument of type C1.
Instance method M1(C1 c) on C1:  this.id = 42, c.ID = 1491
Instance method M1(C1 c) on F:  c.ID = 1491

An instance method on C1 with no arguments.
Instance method M2() on C1:  this.id = 42

A static method on any type, with an argument of type C1.
Static method M3(C1 c) on C1:  c.ID = 42
Static method M3(C1 c) on F:  c.ID = 42

A static method on any type, with an argument of
    that type and an argument of type C1.
Static method M4(C1 c1, C1 c2) on C1:  c1.ID = 42, c2.ID = 1491
Static method M4(F f, C1 c) on F:  c.ID = 1491
*/
open System

// Declare two sample classes, C and F. Class C has an ID
// property so instances can be identified.
type C(id) =
    member _.ID = id 

    member _.M1(c: C) =
        printfn $"Instance method M1(C c) on C:  this.id = {id}, c.ID = {c.ID}"

    member _.M2() =
        printfn $"Instance method M2() on C:  this.id = {id}"

    static member M3(c: C) =
        printfn $"Static method M3(C c) on C:  c.ID = {c.ID}"

    static member M4(c1: C, c2: C) =
        printfn $"Static method M4(C c1, C c2) on C:  c1.ID = {c1.ID}, c2.ID = {c2.ID}"

// Declare a delegate type. The object of this code example
// is to show all the methods this delegate can bind to.
type D = delegate of C -> unit


type F() =
    member _.M1(c: C) =
        printfn $"Instance method M1(C c) on F:  c.ID = {c.ID}"

    member _.M3(c: C) =
        printfn $"Static method M3(C c) on F:  c.ID = {c.ID}"

    member _.M4(f: F, c: C) =
        printfn $"Static method M4(F f, C c) on F:  c.ID = {c.ID}"

[<EntryPoint>]
let main _ =
    let c1 = C 42
    let c2 = C 1491
    let f1 = F()

    // Instance method with one argument of type C.
    let cmi1 = typeof<C>.GetMethod "M1"
    // Instance method with no arguments.
    let cmi2 = typeof<C>.GetMethod "M2"
    // Static method with one argument of type C.
    let cmi3 = typeof<C>.GetMethod "M3"
    // Static method with two arguments of type C.
    let cmi4 = typeof<C>.GetMethod "M4"

    // Instance method with one argument of type C.
    let fmi1 = typeof<F>.GetMethod "M1"
    // Static method with one argument of type C.
    let fmi3 = typeof<F>.GetMethod "M3"
    // Static method with an argument of type F and an argument
    // of type C.
    let fmi4 = typeof<F>.GetMethod "M4"

    printfn "\nAn instance method on any type, with an argument of type C."
    // D can represent any instance method that exactly matches its
    // signature. Methods on C and F are shown here.
    let d = Delegate.CreateDelegate(typeof<D>, c1, cmi1) :?> D
    d.Invoke c2
    let d =  Delegate.CreateDelegate(typeof<D>, f1, fmi1) :?> D
    d.Invoke c2

    Console.WriteLine("\nAn instance method on C with no arguments.")
    // D can represent an instance method on C that has no arguments
    // in this case, the argument of D represents the hidden first
    // argument of any instance method. The delegate acts like a
    // static method, and an instance of C must be passed each time
    // it is invoked.
    let d = Delegate.CreateDelegate(typeof<D>, null, cmi2) :?> D
    d.Invoke c1

    printfn "\nA static method on any type, with an argument of type C."
    // D can represent any static method with the same signature.
    // Methods on F and C are shown here.
    let d = Delegate.CreateDelegate(typeof<D>, null, cmi3) :?> D
    d.Invoke c1
    let d = Delegate.CreateDelegate(typeof<D>, null, fmi3) :?> D
    d.Invoke c1

    printfn "\nA static method on any type, with an argument of"
    printfn "    that type and an argument of type C."
    // D can represent any static method with one argument of the
    // type the method belongs and a second argument of type C.
    // In this case, the method is closed over the instance of
    // supplied for the its first argument, and acts like an instance
    // method. Methods on F and C are shown here.
    let d = Delegate.CreateDelegate(typeof<D>, c1, cmi4) :?> D
    d.Invoke c2
    let test =
        Delegate.CreateDelegate(typeof<D>, f1, fmi4, false)

    // This final example specifies false for throwOnBindFailure
    // in the call to CreateDelegate, so the variable 'test'
    // contains Nothing if the method fails to bind (for
    // example, if fmi4 happened to represent a method of
    // some class other than F).
    match test with
    | :? D as d ->
        d.Invoke c2
    | _ -> ()
    0

// This code example produces the following output:
//     An instance method on any type, with an argument of type C.
//     Instance method M1(C c) on C:  this.id = 42, c.ID = 1491
//     Instance method M1(C c) on F:  c.ID = 1491
//    
//     An instance method on C with no arguments.
//     Instance method M2() on C:  this.id = 42
//    
//     A static method on any type, with an argument of type C.
//     Static method M3(C c) on C:  c.ID = 42
//     Static method M3(C c) on F:  c.ID = 42
//    
//     A static method on any type, with an argument of
//         that type and an argument of type C.
//     Static method M4(C c1, C c2) on C:  c1.ID = 42, c2.ID = 1491
//     Static method M4(F f, C c) on F:  c.ID = 1491
Imports System.Reflection
Imports System.Security.Permissions

' Declare a delegate type. The object of this code example
' is to show all the methods this delegate can bind to.
'
Public Delegate Sub D(ByVal c As C) 

' Declare two sample classes, C and F. Class C has an ID
' property so instances can be identified.
'
Public Class C

    Private _id As Integer

    Public ReadOnly Property ID() As Integer 
        Get
            Return _id
        End Get
    End Property

    Public Sub New(ByVal newId As Integer) 
        Me._id = newId
    End Sub
    
    Public Sub M1(ByVal c As C) 
        Console.WriteLine("Instance method M1(c As C) on C:  this.id = {0}, c.ID = {1}", _
            Me.id, c.ID)
    End Sub
    
    Public Sub M2() 
        Console.WriteLine("Instance method M2() on C:  this.id = {0}", Me.id)
    End Sub
    
    Public Shared Sub M3(ByVal c As C) 
        Console.WriteLine("Shared method M3(c As C) on C:  c.ID = {0}", c.ID)
    End Sub
    
    Public Shared Sub M4(ByVal c1 As C, ByVal c2 As C) 
        Console.WriteLine("Shared method M4(c1 As C, c2 As C) on C:  c1.ID = {0}, c2.ID = {1}", _
            c1.ID, c2.ID)
    End Sub
End Class


Public Class F
    
    Public Sub M1(ByVal c As C) 
        Console.WriteLine("Instance method M1(c As C) on F:  c.ID = {0}", c.ID)
    End Sub
    
    Public Shared Sub M3(ByVal c As C) 
        Console.WriteLine("Shared method M3(c As C) on F:  c.ID = {0}", c.ID)
    End Sub
    
    Public Shared Sub M4(ByVal f As F, ByVal c As C) 
        Console.WriteLine("Shared method M4(f As F, c As C) on F:  c.ID = {0}", c.ID)
    End Sub
End Class

Public Class Example5

    Public Shared Sub Main()

        Dim c1 As New C(42)
        Dim c2 As New C(1491)
        Dim f1 As New F()

        Dim d As D

        ' Instance method with one argument of type C.
        Dim cmi1 As MethodInfo = GetType(C).GetMethod("M1")
        ' Instance method with no arguments.
        Dim cmi2 As MethodInfo = GetType(C).GetMethod("M2")
        ' Shared method with one argument of type C.
        Dim cmi3 As MethodInfo = GetType(C).GetMethod("M3")
        ' Shared method with two arguments of type C.
        Dim cmi4 As MethodInfo = GetType(C).GetMethod("M4")

        ' Instance method with one argument of type C.
        Dim fmi1 As MethodInfo = GetType(F).GetMethod("M1")
        ' Shared method with one argument of type C.
        Dim fmi3 As MethodInfo = GetType(F).GetMethod("M3")
        ' Shared method with an argument of type F and an 
        ' argument of type C.
        Dim fmi4 As MethodInfo = GetType(F).GetMethod("M4")

        Console.WriteLine(vbLf & "An instance method on any type, with an argument of type C.")
        ' D can represent any instance method that exactly matches its
        ' signature. Methods on C and F are shown here.
        '
        d = CType([Delegate].CreateDelegate(GetType(D), c1, cmi1), D)
        d(c2)
        d = CType([Delegate].CreateDelegate(GetType(D), f1, fmi1), D)
        d(c2)

        Console.WriteLine(vbLf & "An instance method on C with no arguments.")
        ' D can represent an instance method on C that has no arguments;
        ' in this case, the argument of D represents the hidden first
        ' argument of any instance method. The delegate acts like a 
        ' Shared method, and an instance of C must be passed each time
        ' it is invoked.
        '
        d = CType([Delegate].CreateDelegate(GetType(D), Nothing, cmi2), D)
        d(c1)

        Console.WriteLine(vbLf & "A Shared method on any type, with an argument of type C.")
        ' D can represent any Shared method with the same signature.
        ' Methods on F and C are shown here.
        '
        d = CType([Delegate].CreateDelegate(GetType(D), Nothing, cmi3), D)
        d(c1)
        d = CType([Delegate].CreateDelegate(GetType(D), Nothing, fmi3), D)
        d(c1)

        Console.WriteLine(vbLf & "A Shared method on any type, with an argument of")
        Console.WriteLine("    that type and an argument of type C.")
        ' D can represent any Shared method with one argument of the
        ' type the method belongs and a second argument of type C.
        ' In this case, the method is closed over the instance of
        ' supplied for the its first argument, and acts like an instance
        ' method. Methods on F and C are shown here.
        '
        d = CType([Delegate].CreateDelegate(GetType(D), c1, cmi4), D)
        d(c2)
        Dim test As [Delegate] =
            [Delegate].CreateDelegate(GetType(D), f1, fmi4, False)

        ' This final example specifies False for throwOnBindFailure 
        ' in the call to CreateDelegate, so the variable 'test'
        ' contains Nothing if the method fails to bind (for 
        ' example, if fmi4 happened to represent a method of  
        ' some class other than F).
        '
        If test IsNot Nothing Then
            d = CType(test, D)
            d(c2)
        End If

    End Sub
End Class

' This code example produces the following output:
'
'An instance method on any type, with an argument of type C.
'Instance method M1(c As C) on C:  this.id = 42, c.ID = 1491
'Instance method M1(c As C) on F:  c.ID = 1491
'
'An instance method on C with no arguments.
'Instance method M2() on C:  this.id = 42
'
'A Shared method on any type, with an argument of type C.
'Shared method M3(c As C) on C:  c.ID = 42
'Shared method M3(c As C) on F:  c.ID = 42
'
'A Shared method on any type, with an argument of
'    that type and an argument of type C.
'Shared method M4(c1 As C, c2 As C) on C:  c1.ID = 42, c2.ID = 1491
'Shared method M4(f As F, c As C) on F:  c.ID = 1491
'

兼容的参数类型和返回类型

使用此方法重载创建的委托的参数类型和返回类型必须与委托表示的方法的参数类型和返回类型兼容;类型不必完全匹配。

如果委托的类型比方法参数的类型更严格,则委托参数的参数与方法的相应参数兼容,因为这样可以保证传递给委托的参数可以安全地传递给该方法。

同样,如果方法的返回类型比委托的返回类型更严格,则委托的返回类型与方法的返回类型兼容,因为这样可以保证方法的返回值可以安全地强制转换为委托的返回类型。

例如,具有类型参数 Hashtable 和返回类型 Object 的委托可以表示具有类型参数 Object 和返回值类型 Hashtable 的方法。

确定委托可以代表的方法

考虑CreateDelegate(Type, Object, MethodInfo)重载提供的灵活性的一种有用方式是,任何给定的委托都可以表示方法签名和方法类型(静态与实例)的四种不同组合。 考虑一个具有类型为 D 的参数的委托类型 C。 下面描述了方法 D 能够代表的内容,忽略返回类型,因为它在所有情况下都必须匹配。

  • D 可以表示具有一个类型为 C 参数的任何实例方法,而不考虑该实例方法属于哪种类型。 当调用 CreateDelegate 时,firstArgumentmethod 所属类型的一个实例,并且称由此生成的委托在该实例上形成闭包。 (简单来说,如果 D 是一个空引用,firstArgument 也可以在空引用上形成闭包。)

  • D 可以表示没有参数的 C 实例方法。 当调用 CreateDelegate 时,firstArgument 是空引用。 生成的委托表示一个开放的实例方法,并且每次调用时都必须提供一个C实例。

  • D 可以表示采用一个类型的 C参数的静态方法,并且该方法可以属于任何类型。 当调用 CreateDelegate 时,firstArgument 是空引用。 生成的委托表示一个打开的静态方法,每次调用它时都必须提供一个实例 C

  • D可以表示属于F类型的静态方法,并且具有两个参数,分别属于F类型和C类型。 调用CreateDelegate 时,firstArgumentF的一个实例。 生成的委托表示在 F 的该实例上形成闭包的静态方法。 请注意,在相同类型的情况下FC,静态方法具有该类型的两个参数。 (在这种情况下,如果 D 是一个空引用,则 firstArgument 在空引用上形成闭包。)

注解

此重载可以为静态方法和打开实例方法委托创建委托;也就是说,显式提供实例方法隐藏的第一个参数的委托。 有关详细说明,请参阅更常规 CreateDelegate(Type, Object, MethodInfo) 的方法重载,该重载允许为实例或静态方法创建打开或关闭的委托的所有组合,还可以选择指定第一个参数。

注释

当委托未在其第一个参数上关闭时,应使用此方法重载,因为在这种情况下,此方法重载的速度会稍快一些。

CreateDelegate 方法会创建指定类型的委托。

CreateDelegate(Type, MethodInfo) 方法

此方法重载等效于调用CreateDelegate(Type, MethodInfo, Boolean)的重载,并为true指定throwOnBindFailure

另请参阅

适用于

CreateDelegate(Type, Type, String)

Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs
Source:
Delegate.cs

创建表示指定类的指定静态方法的指定类型的委托。

public:
 static Delegate ^ CreateDelegate(Type ^ type, Type ^ target, System::String ^ method);
public static Delegate CreateDelegate(Type type, Type target, string method);
[System.Diagnostics.CodeAnalysis.RequiresUnreferencedCode("The target method might be removed")]
public static Delegate CreateDelegate(Type type, Type target, string method);
static member CreateDelegate : Type * Type * string -> Delegate
[<System.Diagnostics.CodeAnalysis.RequiresUnreferencedCode("The target method might be removed")>]
static member CreateDelegate : Type * Type * string -> Delegate
Public Shared Function CreateDelegate (type As Type, target As Type, method As String) As Delegate

参数

type
Type

Type要创建的委托。

target
Type

Type表示实现method的类。

method
String

委托要表示的静态方法的名称。

返回

表示指定类的指定静态方法的委托。

属性

例外

typenull

-或-

targetnull

-或-

methodnull

type 不继承 MulticastDelegate

-或-

type不是 .RuntimeType 请参阅 反射中的运行时类型

-或-

target不是 .RuntimeType

-或-

target 是一种打开的泛型类型。 也就是说,其 ContainsGenericParameters 属性为 true.

-或-

method 不是 static 方法(Visual Basic中的 Shared 方法)。

Invoke找不到方法type

调用方没有访问 method所需的权限。

注解

此方法仅为静态方法创建委托。 实例方法是与类实例关联的方法;静态方法是与类本身关联的方法。

此方法重载等效于调用CreateDelegate(Type, Type, String, Boolean, Boolean)方法重载,指定falseignoreCasetrue指定throwOnBindFailure方法重载。

另请参阅

适用于