Delegate クラスは、デリゲート型の基本クラスです。ただし、システムとコンパイラに限り、Delegate クラスまたは MulticastDelegate クラスから明示的に派生させることができます。デリゲート型から新しい型を派生させることはできません。Delegate クラスは、デリゲート型とは見なされません。このクラスは、デリゲート型を派生させるために使用されるクラスです。
ほとんどの言語では delegate キーワードが実装されています。また、それらの言語のコンパイラは MulticastDelegate クラスから派生させることができます。このため、開発者は各言語で提供されている delegate キーワードを使用する必要があります。
共通言語ランタイムには、継承されたメソッドに加えて、BeginInvoke および EndInvoke というデリゲート型用の 2 つの特別なメソッドが用意されています。これらのメソッドの詳細については、「同期メソッドの非同期呼び出し」を参照してください。
デリゲート型の宣言によって、1 つ以上のメソッドのシグネチャを指定するコントラクトを確立します。デリゲートは、次の参照先を持つデリゲート型のインスタンスです。
型のインスタンス メソッドと、その型に適用できるターゲット オブジェクト。
仮パラメータ リストに非表示の this パラメータを指定した、型のインスタンス メソッド。デリゲートは、オープンなインスタンス デリゲートであると言います。
静的メソッド。
静的メソッドと、そのメソッドの最初のパラメータに適用できるターゲット オブジェクト。デリゲートは、その最初の引数に対して閉じられていると言います。
デリゲート バインディングの詳細については、「共通型システムのデリゲート」と「CreateDelegate(Type, Object, MethodInfo, Boolean)」を参照してください。
メモ : |
|---|
.NET Framework Version 1.0 および Version 1.1 では、メソッドのシグネチャがデリゲート型で指定されたシグネチャと完全に一致する場合にのみ、デリゲートはメソッドを表すことができます。つまり、上述の最初の項目と 3 番目の項目のみがサポートされ、最初の項目では完全な型の一致が必要です。 |
デリゲートが最初の引数に対して閉じられたインスタンス メソッドを表している場合 (最も一般的)、デリゲートは、メソッドのエントリ ポイントへの参照と、そのメソッドを定義した型に適用可能な型である、ターゲットと呼ばれるオブジェクトへの参照を格納します。デリゲートがオープンなインスタンス メソッドを表している場合、デリゲートはそのメソッドのエントリ ポイントへの参照を格納しています。デリゲート シグネチャは、仮パラメータ リストに非表示の this パラメータを含める必要があります。この場合、デリゲートはターゲット オブジェクトへの参照を持ちません。デリゲートを呼び出すときに、ターゲット オブジェクトを指定する必要があります。
デリゲートが静的メソッドを表している場合、デリゲートはそのメソッドのエントリ ポイントへの参照を格納しています。デリゲートが最初の引数に対して閉じている静的メソッドを表している場合、デリゲートはメソッドのエントリ ポイントへの参照と、そのメソッドの最初の引数の型に適用できるターゲット オブジェクトへの参照を格納しています。デリゲートを呼び出したときに、最初の静的メソッドの引数はターゲット オブジェクトを受け取ります。
デリゲートの呼び出しリストは、順序付けられたデリゲートのセットであり、呼び出しリスト内の各要素はデリゲートによって呼び出されるメソッドを 1 つずつ表します。呼び出しリストには、重複メソッドを格納できます。デリゲートがメソッドを呼び出すときは、呼び出しリストに出現する順にメソッドを呼び出します。デリゲートは呼び出しリスト内のすべてのメソッドを呼び出そうとします。重複メソッドは、呼び出しリストに出現するたびに呼び出されます。デリゲートは不変であるため、デリゲートの呼び出しリストを一度作成すると、そのリストは変わりません。
複数のメソッドを呼び出したり、組み合わせ演算で使用できるデリゲートを、それぞれ "マルチキャスト デリゲート" および "組み合わせ可能デリゲート" と呼びます。
Combine、Remove などの組み合わせ演算によって既存のデリゲートが変更されることはありません。その代わり、組み合わせ演算では、演算の結果、または変更されないデリゲート、または nullNothingnullptrnull 参照 (Visual Basic では Nothing) が格納された新しいデリゲートが返されます。演算の結果がメソッドをまったく参照していないデリゲートの場合は、nullNothingnullptrnull 参照 (Visual Basic では Nothing) が返されます。要求した演算が無効の場合は、変更されないデリゲートが返されます。
呼び出されたメソッドが例外をスローした場合は、メソッドが実行を中止し、デリゲートの呼び出し元に例外が戻され、呼び出しリスト内の残りのメソッドは呼び出されません。呼び出し元で例外がキャッチされても、この動作は変わりません。
デリゲートが呼び出したメソッドのシグネチャに戻り値が含まれる場合、デリゲートは呼び出しリスト内の最後の要素の戻り値を返します。参照渡しされたパラメータがシグネチャに含まれる場合、そのパラメータの最終的な値は、呼び出しリスト内のすべてのメソッドが順次実行されたことによって更新された結果の値になります。
デリゲートに最も近い C または C++ の機能は関数ポインタです。デリゲートは、静的メソッドまたはインスタンス メソッドを表すことができます。デリゲートがインスタンス メソッドを表している場合、デリゲートは、そのメソッドのエントリ ポイントへの参照だけでなく、クラス インスタンスへの参照も格納しています。関数ポインタとは異なり、デリゲートはオブジェクト指向のタイプ セーフな機能です。