次の方法で共有


デリゲート (Visual Basic)

デリゲートは、メソッドを参照するオブジェクトです。 これらは、他のプログラミング言語で使用される関数ポインターに似ているため、 型セーフ な関数ポインターとして記述されることがあります。 ただし、関数ポインターとは異なり、Visual Basic デリゲートはクラス System.Delegateに基づく参照型です。 デリゲートは、共有メソッド (クラスの特定のインスタンスなしで呼び出すことができるメソッド) とインスタンス メソッドの両方を参照できます。

デリゲートとイベント

デリゲートは、呼び出し元のプロシージャと呼び出されるプロシージャの間に仲介者が必要な場合に便利です。 たとえば、イベントを発生させるオブジェクトが、さまざまな状況で異なるイベント ハンドラーを呼び出せるようにしたい場合があります。 残念ながら、イベントを発生させるオブジェクトは、特定のイベントを処理しているイベント ハンドラーを事前に認識できません。 Visual Basic では、 AddHandler ステートメントを使用するときにデリゲートを作成することで、イベント ハンドラーをイベントに動的に関連付けることができます。 実行時に、デリゲートは適切なイベント ハンドラーに呼び出しを転送します。

独自のデリゲートを作成することはできますが、ほとんどの場合、Visual Basic によってデリゲートが作成され、詳細が自動的に処理されます。 たとえば、 Event ステートメントは、 <EventName>EventHandler という名前のデリゲート クラスを、 Event ステートメントを含むクラスの入れ子になったクラスとして、イベントと同じシグネチャを持つデリゲート クラスを暗黙的に定義します。 AddressOf ステートメントは、特定のプロシージャを参照するデリゲートのインスタンスを暗黙的に作成します。 次の 2 行のコードは同等です。 最初の行では、 EventHandlerのインスタンスが明示的に作成され、メソッドへの参照 Button1_Click 引数として送信されます。 2 行目は、同じことを行うためのより便利な方法です。

AddHandler Button1.Click, New EventHandler(AddressOf Button1_Click)
' The following line of code is shorthand for the previous line.
AddHandler Button1.Click, AddressOf Me.Button1_Click

コンパイラがコンテキストによってデリゲートの型を決定できる任意の場所でデリゲートを簡単に作成する方法を使用できます。

既存のデリゲート型を使用するイベントの宣言

場合によっては、既存のデリゲート型を基になるデリゲートとして使用するイベントを宣言することが必要な場合があります。 次の構文は、その方法を示しています。

Delegate Sub DelegateType()
Event AnEvent As DelegateType

これは、複数のイベントを同じハンドラーにルーティングする場合に便利です。

デリゲート変数とパラメーター

空きスレッド処理や、実行時に異なるバージョンの関数を呼び出す必要があるプロシージャなど、イベントに関連しないその他のタスクにデリゲートを使用できます。

たとえば、自動車の名前を含むリスト ボックスを含む、分類された広告アプリケーションがあるとします。 広告はタイトルで並べ替えられます。これは通常、自動車のメーカーです。 あなたが直面する可能性のある問題は、一部の車がメイク前の車の年を含むときに発生します。 問題は、リスト ボックスの組み込みの並べ替え機能が文字コードによってのみ並べ替えられるということです。日付から始まるすべての広告が最初に配置され、その後にメイクから始まる広告が表示されます。

これを解決するには、ほとんどのリスト ボックスで標準のアルファベット順の並べ替えを使用するクラスで並べ替えプロシージャを作成できますが、実行時に自動車広告のカスタム並べ替え手順に切り替えることができます。 これを行うには、デリゲートを使用して、実行時にカスタム並べ替えプロシージャを並べ替えクラスに渡します。

AddressOf およびラムダ式

各デリゲート クラスは、オブジェクト メソッドの仕様に渡されるコンストラクターを定義します。 デリゲート コンストラクターの引数は、メソッドまたはラムダ式への参照である必要があります。

メソッドへの参照を指定するには、次の構文を使用します。

AddressOf [expression.]methodName

expressionのコンパイル時の型は、デリゲート クラスのシグネチャと一致するシグネチャを持つ、指定した名前のメソッドを含むクラスまたはインターフェイスの名前である必要があります。 methodNameには、共有メソッドまたはインスタンス メソッドのいずれかを指定できます。 クラスの既定のメソッドのデリゲートを作成する場合でも、 methodName は省略可能ではありません。

ラムダ式を指定するには、次の構文を使用します。

Function ([parm As type, parm2 As type2, ...]) expression

次の例は、デリゲートの参照を指定するために使用される AddressOf 式とラムダ式の両方を示しています。

Module Module1

    Sub Main()
        ' Create an instance of InOrderClass and assign values to the properties.
        ' InOrderClass method ShowInOrder displays the numbers in ascending 
        ' or descending order, depending on the comparison method you specify.
        Dim inOrder As New InOrderClass
        inOrder.Num1 = 5
        inOrder.Num2 = 4

        ' Use AddressOf to send a reference to the comparison function you want
        ' to use.
        inOrder.ShowInOrder(AddressOf GreaterThan)
        inOrder.ShowInOrder(AddressOf LessThan)

        ' Use lambda expressions to do the same thing.
        inOrder.ShowInOrder(Function(m, n) m > n)
        inOrder.ShowInOrder(Function(m, n) m < n)
    End Sub

    Function GreaterThan(ByVal num1 As Integer, ByVal num2 As Integer) As Boolean
        Return num1 > num2
    End Function

    Function LessThan(ByVal num1 As Integer, ByVal num2 As Integer) As Boolean
        Return num1 < num2
    End Function

    Class InOrderClass
        ' Define the delegate function for the comparisons.
        Delegate Function CompareNumbers(ByVal num1 As Integer, ByVal num2 As Integer) As Boolean
        ' Display properties in ascending or descending order.
        Sub ShowInOrder(ByVal compare As CompareNumbers)
            If compare(_num1, _num2) Then
                Console.WriteLine(_num1 & "  " & _num2)
            Else
                Console.WriteLine(_num2 & "  " & _num1)
            End If
        End Sub

        Private _num1 As Integer
        Property Num1() As Integer
            Get
                Return _num1
            End Get
            Set(ByVal value As Integer)
                _num1 = value
            End Set
        End Property

        Private _num2 As Integer
        Property Num2() As Integer
            Get
                Return _num2
            End Get
            Set(ByVal value As Integer)
                _num2 = value
            End Set
        End Property
    End Class
End Module

関数のシグネチャは、デリゲート型のシグネチャと一致する必要があります。 ラムダ式について詳しくは、「ラムダ式」をご覧ください。 ラムダ式とデリゲートへの AddressOf 割り当てのその他の例については、「 緩やかなデリゲート変換」を参照してください。

タイトル 説明
方法: デリゲート メソッドを呼び出す メソッドをデリゲートに関連付け、デリゲートを使用してそのメソッドを呼び出す方法を示す例を示します。
方法: Visual Basic でプロシージャを別のプロシージャに渡す デリゲートを使用して、あるプロシージャを別のプロシージャに渡す方法を示します。
緩やかなデリゲート変換 シグネチャが同一でない場合でも、デリゲートまたはハンドラーにサブと関数を割り当てる方法について説明します
イベント Visual Basic のイベントの概要について説明します。