In the first variant of your code, you're not doing anything to manage the cancellation token.
For example, you're not checking whether token.IsCancellationRequested
returns true
(and then throwing an exception) or calling ThrowIfCancellationRequested()
from your CancellationToken object.
Also, the Task.Run
overload you used checks whether the token is already canceled or not when the task is about to start and your code states that token will report cancellation after 500 ms.
So, your code is just ignoring the cancellation request and that's why the task ran to completion.
You should do something like this:
void Main()
{
var ct = new CancellationTokenSource(500).Token;
var v =
Task.Run(() =>
{
Thread.Sleep(1000);
ct.ThrowIfCancellationRequested();
return 10;
}, ct).Result;
Console.WriteLine(v); //now a TaskCanceledException is thrown.
Console.Read();
}
or this, without passing the token, as others already noted:
void Main()
{
var ct = new CancellationTokenSource(500).Token;
ct.ThrowIfCancellationRequested();
var v =
Task.Run(() =>
{
Thread.Sleep(1000);
return 10;
}).Result;
Console.WriteLine(v); //now a TaskCanceledException is thrown.
Console.Read();
}
The second variant of your code works, because you're already initializing a token with a Canceled
state set to true. Indeed, as stated here:
If canceled is true, both CanBeCanceled and IsCancellationRequested will be true
the cancellation has already been requested and then the exception TaskCanceledException
will be immediately thrown, without actually starting the task.