async - stay on the current thread?

坚强是说给别人听的谎言 提交于 2019-11-26 15:28:51

The async/await support was added to help programmers write GUIs that don't freeze. Particularly useful in Store apps, and the core reason it was added to C# v5, WinRT is a pretty unfriendly api that has many asynchronous methods.

The "stay on the same thread" scenario is very important in a GUI app, required because a GUI isn't thread-safe. It does however require a message loop, the only way to get asynchronous code to resume on the same thread. The message loop is the core solution to the producer-consumer problem. Clearly your program doesn't have one, looks a lot like a console mode app. You therefore don't get this behavior, it resumes on a worker thread.

Not much of a problem, you don't actually need it to resume on the same thread since a console is thread-safe anyway. Well, mostly, not counting the lock that was added in .NET 4.5 when you ask for input. Which of course also means that you don't have a heckofalot of use for async/await either, a Task works fine as well.

If I execute an asynchronous method and it runs, it surely runs on another thread.

No, it typically runs on another thread. It does not surely run on another thread.

Stop thinking about threads for a moment and think about the nature of asynchrony. The nature of asynchrony is:

  • I've got some workflow that I am currently executing.
  • I can't proceed in this workflow until I get information X.
  • I'm going to do something else until I get information X.
  • At some point in the future, once I have X, I'm going to come back to where I left off in my workflow and continue.

Suppose you're doing your taxes and in the middle of this complicated workflow you have a large addition to perform. You can perform a few operations then remember where you are, and go have lunch. Then come back and perform a few more operations, then remember where you are, and feed the cat. Then come back and perform a few more operations, then remember where you are, and wash the dishes. Then finish off the calculations, and resume where you left off in your workflow.

That's an asynchronous calculation but it only needed a single worker to do it. Having multiple workers is just a particularly convenient way to do asynchrony, it is not a requirement.

Eric Lippert's "thread" terminology is simplified. I have an async/await intro on my blog that explains how await will capture the current context and use that to resume the async method.

If you are in a UI context, then the context is the single UI thread, and the async method will resume on that thread. Otherwise, the rules are a bit more complicated. In particular, Console apps do not provide any context, so async methods by default resume on the thread pool.

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!