1

次のコードを見てください。

そこで、現在のコンテキスト (WinForms スレッド) を取得し、そのコンテキストで新しいタスクを開始し、タスク スケジューラで同期継続をアタッチしDefaultます。私が理解している限り、継続はスレッドプールスレッドで開始する必要があります。UI スレッドがスレッドプールに属していません。しかし、代わりに、継続を含むすべてのコードが同じスレッドで同期して実行されます。それは私にとってかなり予想外です。

ところで、継続オプションを に設定すると、必要にTaskContinuationOptions.None応じて別のスレッドで実行されます。継続オプションはタスク スケジューラよりも優先されるようですが、それらは単なるヒントであり、スケジューラは必須です。

TaskScheduler uiContext = TaskScheduler.FromCurrentSynchronizationContext();
Console.WriteLine("start thread {0}", Thread.CurrentThread.ManagedThreadId);

Task.Factory.StartNew(() =>
{
    Console.WriteLine("ui thread {0}", Thread.CurrentThread.ManagedThreadId);
}, CancellationToken.None, TaskCreationOptions.None, uiContext).ContinueWith(t =>
{
    Console.WriteLine("continuation thread {0}", Thread.CurrentThread.ManagedThreadId);
}, CancellationToken.None, TaskContinuationOptions.ExecuteSynchronously, TaskScheduler.Default);

それはバグですか、それとも予想される動作ですか?

親タスクのコンテキストと継続オプションに関係なく、UI スレッドの外部で継続コードの実行を保証するにはどうすればよいですか? カスタムタスクスケジューラ?

注: これがレガシー コードであることはわかっており、async/await を使用することをお勧めします。

4

0 に答える 0