1

私が次のようなものを書くと

myDataModel.ContentLoaded += (o,e) => { DoSomething(); }

その匿名の代理人はいつ(もしあれば)イベントから削除されますか?

簡単な例として、私はこのプログラムを書くことができます

class Program
{
    public event EventHandler<EventArgs> MyEvent = delegate { };

    static void Main(string[] args)
    {
        Program p = new Program();
        while(true)
        {
            p.MyEvent += (o, e) => Console.WriteLine("Hello!");

            Console.ReadLine();
            p.Foo();
        }
    }

    void Foo()
    {
        MyEvent(this, EventArgs.Empty);
    }
}

そして、「Enter」を繰り返し押したときの出力は

Hello!

Hello!
Hello!

Hello!
Hello!
Hello!

Hello!
Hello!
Hello!
Hello!

...など。行を追加できます

p.MyEvent -= (o, e) => Console.WriteLine("Hello!");

その後p.Foo()ですが、まったく別の匿名の代理人を削除するため、もちろん効果はありません。

それで、これとの取引は何ですか?これらの匿名の代理人を削除する方法はありますか?たとえば、次のような式を使用してデータをプルする非同期Silverlightアプリケーションの意味は何ですか?

_myDataContext.Load(myQuery, loadOperation =>
    {
        // do stuff with the data here
    }, null);

?これらの種類のコールバックはイベントを使用して実装されていないと思いますが、もちろんそれを伝えることは不可能です(?)。

注意深く説明されていない場合、匿名の代表者は危険ですか?

4

2 に答える 2

1

イベントから自動的に削除されることはありません。

匿名の代理人の登録を解除する場合は、次の質問を確認してください。

C#で匿名メソッドの購読を解除する

于 2011-02-25T02:04:42.973 に答える
1

最初に変数に割り当てなかったデリゲートを削除する(簡単な)方法はありません。彼らが匿名であるかどうかは実際には問題ではありません。匿名デリゲートを変数に割り当て、後で削除することができます。

EventHandler eh = (src, e) => Console.WriteLine("Hello");
form.Click += eh; 
// At some later point
form.Click -= eh;

同様に、以下を使用して登録した場合、デリゲートを削除する(簡単な)方法はありません。

form.Click += new EventHandler(foo);

イベントの問題は、アタッチされているオブジェクトがガベージコレクションされている場合にのみガベージコレクションされることです(イベントが処理するターゲットオブジェクトがプログラムの他の部分から参照されていないため、有用な作業を実行できない場合でも) )。

これは、弱いイベントを使用して解決できます。それらを明示的に削除する代わりに、GCがそれらを自動的に処理できるようにするいくつかのメカニズムを使用します。

于 2011-02-25T02:05:26.590 に答える