title: How does C# 5.0's async-await feature differ from the TPL?
body: <p>I don't see the different between C#'s (and VB's) new async features, and .NET 4.0's <a href="https://docs.microsoft.com/en-us/dotnet/standard/parallel-programming/task-based-asynchronous-programming" rel="nofollow noreferrer">Task Parallel Library</a>. Take, for example, Eric Lippert's code <a href="https://web.archive.org/web/20151017040918/http://blogs.msdn.com:80/b/ericlippert/archive/2010/10/29/asynchronous-programming-in-c-5-0-part-two-whence-await.aspx" rel="nofollow noreferrer">from here</a>:</p>
  <pre><code>async void ArchiveDocuments(List&lt;Url&gt; urls) {
      Task archive = null;
      for(int i = 0; i &lt; urls.Count; ++i) {
          var document = await FetchAsync(urls[i]);
          if (archive != null)
              await archive;
          archive = ArchiveAsync(document);
      }
  }
  </code></pre>
  <p>It seems that the <code>await</code> keyword is serving two different purposes. The first occurrence (<code>FetchAsync</code>) seems to mean, <em>&quot;If this value is used <strong>later in the method</strong> and its task isn't finished, wait until it completes before continuing.&quot;</em> The second instance (<code>archive</code>) seems to mean, <em>&quot;If this task is not yet finished, wait <strong>right now</strong> until it completes.&quot;</em> If I'm wrong, please correct me.</p>
  <p>Couldn't it just as easily be written like this?</p>
  <pre><code>void ArchiveDocuments(List&lt;Url&gt; urls) {
      for(int i = 0; i &lt; urls.Count; ++i) {
          var document = FetchAsync(urls[i]);       // removed await
          if (archive != null)
              archive.Wait();                       // changed to .Wait()
          archive = ArchiveAsync(document.Result);  // added .Result
      }
  }
  </code></pre>
  <p>I've replaced the first <code>await</code> with a <code>Task.Result</code> where the value is actually needed, and the second <code>await</code> with <code>Task.Wait()</code>, where the wait is actually occurring. The functionality is <code>(1)</code> already implemented, and <code>(2)</code> much closer semantically to what is actually happening in the code.</p>
  <p>I do realize that an <code>async</code> method is rewritten as a state machine, similar to iterators, but I also don't see what benefits that brings. Any code that requires another thread to operate (such as downloading) will still require another thread, and any code that doesn't (such as reading from a file) could still utilize the TPL to work with only a single thread.</p>
  <p>I'm obviously missing something huge here; can anybody help me understand this a little better?</p>