Chapter 13. Scheduling

When a piece of code executes, it has to run on some thread somewhere. A scheduler is an object that decides where a certain piece of code runs. There are a few different scheduler types in the .NET framework, and they’re used with slight differences by parallel and dataflow code.

I recommend that you not specify a scheduler whenever possible; the defaults are usually correct. For example, the await operator in asynchronous code will automatically resume the method within the same context unless you override this default, as described in Recipe 2.7. Similarly, reactive code has reasonable default contexts for raising its events, which you can override with ObserveOn, as described in Recipe 6.2.

If you need other code to execute in a specific context (e.g., a UI thread context or an ASP.NET request context), then you can use the scheduling recipes in this chapter to control the scheduling of your code.

13.1 Scheduling Work to the Thread Pool

Problem

You have a piece of code that you explicitly want to execute on a threadpool thread.

Solution

The vast majority of the time, you’ll want to use Task.Run, which is quite simple. The following code blocks a threadpool thread for 2 seconds:

Task task = Task.Run(() =>
{
  Thread.Sleep(TimeSpan.FromSeconds(2));
});

Task.Run also understands return values and asynchronous lambdas just fine. The task returned by Task.Run in the following code will complete after 2 seconds with a result of 13:

Task<int> task = Task ...

Get Concurrency in C# Cookbook, 2nd Edition now with the O’Reilly learning platform.

O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.