2

擬似コード:

class A
{
    Dictionary<string, object> dic = new Dictionary<string, object>();
    public Do()
    {
        some_a.SomeEvent += (s, e) =>
                 {
                     dic["some_string"] = new object();
                 };   
         dic["some_other_string"] = new object();
    }
}

これは安全ですか?両方のディクショナリ操作が単一の同じスレッド上にある場合です。そうですか?

編集私の状況では、イベントはと同じスレッドDoで発生するので、安全です。

4

3 に答える 3

3

イベントハンドラー内のコードは、イベントが発生したスレッドで実行されます。

class AsyncWorker
{
    public void BeginWork()
    {
        new TaskFactory().StartNew(() => RaiseMyEvent());
    }

    public event EventHandler MyEvent;

    private void RaiseMyEvent()
    {
        var myEvent = MyEvent;
        if(myEvent != null)
            myEvent(EventArgs.Empty);
    }
}

var worker = new AsyncWorker();
worker.MyEvent += (s, e) =>
                  {
                      /* I will be executed on the thread
                         started by the TaskFactory */
                  };
worker.BeginWork();
于 2012-08-17T10:39:11.577 に答える
3

イベントは(通常)イベントを呼び出すスレッドで発生します。したがって、イベントが呼び出される原因となるコードを表示しないため、実際に完全にコメントすることはできません。

厳密に言えば、イベントは任意のスレッドで発生する可能性があります-ランダムスレッドが呼び出しているためOnSomeEvent(またはトリガーが何であれ)、またはOnSomeEvent実装がBeginInvoke何らかの理由で使用することを選択した場合、これはありそうにありません。

最終的には、次のようになります。このコードに複数のスレッドが関与していると考える理由はありますか。

しかし:絶対にそうではないこと:いいえ、それをサブスクライブするスレッドでそのイベントを自動的に発生させるものは何もありません。イベントサブスクリプションは、オブジェクトとメソッドのペアにすぎません。サブスクリプションで指定されたスレッドはありません。

于 2012-08-17T10:39:14.503 に答える
1

特に別のスレッドでイベントハンドラーを開始しない限り、両方の操作は実際には同じスレッドで実行されます(シングルスレッドアプリケーションを想定)。

于 2012-08-17T10:39:05.273 に答える