How can I run both of these methods ‘at the same time’ in .NET 4.5?

Here is what you may want to do:

public async Task<PewPew> SomeMethod(Foo foo)
{
    // get the stuff on another thread 
    var cTask = Task.Run(() => GetAllTheCats(foo));
    var fTask = Task.Run(() => GetAllTheFood(foo));

    var cats = await cTask;
    var food = await fTask;

    return new PewPew
               {
                   Cats = cats,
                   Food = food
               };
}

public IList<Cat> GetAllTheCats(Foo foo)
{
    // Do stuff, like hit the Db, spin around, dance, jump, etc...
    // It all takes some time.
    return cats;
}

public IList<Food> GetAllTheFood(Foo foo)
{
    // Do more stuff, like hit the Db, nom nom noms...
    // It all takes some time.
    return food;
}

There are two things you need to understand here:

  1. What is diff between this:

    var cats = await cTask;
    var food = await fTask;

And this:

Task.WaitAll(new [] {cTask, fTask});

Both will give you similar result in the sense let the 2 async tasks finish and then return new PewPew – however, difference is that Task.WaitAll() will block the current thread (if that is UI thread, then UI will freeze). instead, await will break down the SomeMethod say in a state machine, and return from the SomeMethod to its caller as it encounters await keyword. It will not block the thread. The Code below await will be scheduled to run when async task is over.

  1. You could also do this:

    var cats = await Task.Run(() => GetAllTheCats(foo));
    var food = await Task.Run(() => GetAllTheFood(foo));

However, this will not start the async tasks simultaneously. Second task will start after the first is over. This is because how the await keyword works.

EDIT: How to use SomeMethod – somewhere at the start of the call tree, you have to use Wait() or Result property – OR – you have to await from async void.
Generally, async void would be an event handler:

public async void OnSomeEvent(object sender, EventArgs ez) 
{ 
  Foo f = GetFoo();
  PewPew p = await SomeMethod(f);
}

If not then use Result property.

public Foo2 NonAsyncNonVoidMethod() 
{
   Foo f = GetFoo();
   PewPew p = SomeMethod(f).Result; //But be aware that Result will block thread
  
   return GetFoo2(p);
}

Leave a Comment