動機
を使用してスローされた例外を処理し、メイン UI スレッドで例外を再スローTask
するWindows.Forms
アプリケーションで を使用しています。Task
Task.ContinueWith()
Control.Invoke()
ただし、使用すると例外に気付くことができませんでしたが、使用するControl.Invoke()
と機能しますControl.BeginInvoke()
。
で動作しない理由とControl.Invoke()
、動作させる方法を知っている人はいますか?
回避策
私は現在、使用Control.BeginInvoke()
する代わりに投げるために使用していますControl.Invoke()
再現する手順
環境: Windows 7 x64、Visual Studio 2012、.Net 4 用にコンパイル (ただし、.Net 4.5 は VS2012 の一部としてインストールされます)。
(1) というフォームで既定の Windows フォーム アプリを作成しますform1
。
(2) というフォームにボタンを配置し、button1
というハンドラーを追加しbutton1_Click()
ます。
(3) 次のように実装button1_Click()
します。
private void button1_Click(object sender, EventArgs e)
{
Task.Factory.StartNew(() =>
{
Thread.Sleep(1000);
this.BeginInvoke(new Action(() =>
{
throw new InvalidOperationException("TEST");
}));
});
}
(4) プログラムを実行し、 ボタンをクリックします。1 秒後、期待どおりに例外ダイアログが表示されます。
(5) に変更this.BeginInvoke
しthis.Invoke
ます。
(6) プログラムを再度実行し、 ボタンをクリックします。これで、例外は黙って無視されます!
指定された の UI スレッドでInvoke()
との両方が実行されるため、例外が無視される理由と無視されない理由がわかりません...BeginInvoke()
Control
例外がスローされた場合に返されないという事実と関係があるに違いないと推測していますControl.Invoke()
が、例外が(明らかに)完全に無視されることを意味する理由を理解しようとすると、頭が痛くなります。