I have been trying to get my head around C#'s new async/await and Task.Run functionality recently. In doing so I wrote some simple test code that writes to the console so that I can see in what order things happen in, throwing in a Thread.Sleep here and there to make sure things really happens in the order I expected.
Here is one of my tests
[Test]
public void TaskRun()
{
Console.WriteLine("Before");
Task.Run(() => Console.WriteLine(_terminator.IWillBeBack()));
Console.WriteLine("After");
}
with the following Terminator class:
public class Terminator
{
public string IWillBeBack()
{
return "I will be back";
}
}
From this I expected the result to most likely be Before, After, and then I will be back. This is indeed what happens. Then I make a change to the IWillBeBack-method to allow it to sleep for 3 seconds. The code for this:
public class Terminator
{
public string IWillBeBack()
{
Thread.Sleep(3000);
return "I will be back";
}
}
I expected the result to still be Before, After, and then after 3 seconds again I will be back. This is not what happens though. I instead get Before and After, but never I will be back.
Why is this?
When I debug it clearly goes through the code, sleeping and returning. I don't need Thread.Sleep in this way in any production code, but I would like to have a vague understanding of why I will be back is not written to the console in the second case.
Your test is completing before it tries to print "I will be back". You're not doing anything to wait until that's finished. Depending on the test runner, however it's redirecting Console.WriteLine
may have been disconnected as soon as the test has finished.
If you want to see it finish, change your test to:
[Test]
public void TaskRun()
{
Console.WriteLine("Before");
var task = Task.Run(() => Console.WriteLine(_terminator.IWillBeBack()));
Console.WriteLine("After");
task.Wait();
}
If you use the MS Test framework in VS 2012 you can also write the test like this
[TestMethod]
public async Task TaskRun()
{
Console.WriteLine("Before");
Task t = Task.Run(() => Console.WriteLine(IWillBeBack()));
Console.WriteLine("After");
await t;
}
private string IWillBeBack()
{
Thread.Sleep(3000);
return "I will be back";
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With