これを達成する簡単な方法はありません。
好ましいアプローチ:
デリゲートを保存することはできませんなぜ私は表示されません。インスタンスをいくつかのフィールドとして保存する必要はありません。それはあなたの匿名のイベントハンドラによって捕獲されたローカル変数になります
EventHandler<TypeOfEventArgs> handler = null;
handler = (s, e) =>
{
// Do whatever you need to do here
// Remove event:
foo.Event -= handler;
}
foo.Event += handler;
私はあなたがこれを使用することはできません、単一のシナリオを考えることはできません。デリゲートを保存せずに
代替アプローチ:
あなたはこのようなシナリオを持っている場合は、それはかなりのトリッキー取得します。
イベントへのハンドラとして追加されたデリゲートを見つける必要があります。あなたがそれを保存しなかったので、それを得るのはかなり難しいです。現在実行中のメソッドのデリゲートを取得するには、this
はありません。それは、+=
と-=
すなわちを追加し、ハンドラを削除するに制限されている中で定義されたクラス外のイベントにアクセスするため
あなたは、どちらかのイベントでGetInvocationList()
を使用することはできません。
新しい代理人を作成することもできません。匿名メソッドを定義するMethodInfo
オブジェクトにアクセスすることはできますが、メソッドが宣言されているクラスのインスタンスにはアクセスできません。このクラスはコンパイラによって自動的に生成され、匿名メソッド内のthis
を呼び出すと、あなたの通常のメソッドが定義されているクラスのインスタンスです。
私が見つけた唯一の方法は、イベントが使用するフィールドを見つけてGetInvocationList()
を呼び出すことです。次のコードでは、ダミーのクラスでこれを示しています。
void Main()
{
var foo = new Foo();
foo.Bar += (s, e) => {
Console.WriteLine("Executed");
var self = new StackFrame().GetMethod();
var eventField = foo.GetType()
.GetField("Bar", BindingFlags.NonPublic |
BindingFlags.Instance);
if(eventField == null)
return;
var eventValue = eventField.GetValue(foo) as EventHandler;
if(eventValue == null)
return;
var eventHandler = eventValue.GetInvocationList()
.OfType<EventHandler>()
.FirstOrDefault(x => x.Method == self)
as EventHandler;
if(eventHandler != null)
foo.Bar -= eventHandler;
};
foo.RaiseBar();
foo.RaiseBar();
}
public class Foo
{
public event EventHandler Bar;
public void RaiseBar()
{
var handler = Bar;
if(handler != null)
handler(this, EventArgs.Empty);
}
}
GetField
に渡された文字列"Bar"
は、イベントで使用されているフィールドの正確な名前にする必要がありますのでご注意ください。この結果、2つの問題が発生する。
- フィールドの名前は異なる場合があります。明示的なイベント実装を使用する場合フィールド名は手動で検索する必要があります。
- フィールドが全くない可能性があります。これは、イベントが明示的なイベント実装を使用し、別のイベントにデリゲートするか、デリゲートを別の方法で格納する場合に発生します。
結論:
別のアプローチは、実装の詳細に依存しているので、あなたはそれを避けることができれば、それを使用しないでください。
。 [this](http://martinfowler.com/eaaDev/EventAggregator.html)をご覧ください。イベントアグリゲータを購読/購読解除する方法について説明しています(この場合は画面についてです)。実際のアグリゲータはオブジェクト間の参照を作成します。そこにはさまざまな実装があります。私が好むものは[Caliburn.Micro](http://www.mindscapehq.com/blog/index.php/2012/02/01/caliburn-micro-part-4-the-event-aggregator/)に実装されています。 。 –