简体   繁体   中英

What is the relationship between Boost::Asio and C++20 coroutines?

I started trying to learn Boost::Asio by reading the documentation and example code . I found things difficult to understand, particularly because the model seemed similar to coroutines.

I then decided to learn about coroutines, starting with this cppcon talk . In the linked talk, the following line was given in an example of coroutine usage. The example was written in 2014, so the syntax may not match C++20 coroutines.

auto conn = await Tcp::connect.Read("127.0.0.1", 1337)

This feels similar to the stated goals of Boost::Asio. However, in the examples section of the Boost::Asio documentation, there is an example that mixes Boost::Asio and C++20 coroutines. (I do not yet understand this example.)

What is the relationship between Boost::Asio and coroutines? Do coroutines replace parts of Boost::Asio? If I am not doing networking, should I still use Boost::Asio? Where do std::async and the senders/receivers proposal fit into all this?

Q. What is the relationship between Boost::Asio and coroutines?

C++20 coroutines are one of the completion token mechanisms provided with any Asio compliant async API

Q. Do coroutines replace parts of Boost::Asio?

Not 1 on 1.

In practice people may feel a lot less need to write asio::spawn (stackful) coroutines, because in practice the stackfulness is rarely required and makes the implementation (very) heavy in comparison. Also, up to Boost 1.81(?) asio::spawn will still depend on Boost Coroutine (work is underway to remove that and implement the functionality directly on top of Boost Context).

Another where C++20 coroutines seem to remove friction is when providing a dual API (sync and async). I've heard people suggest that it is possible to implement the synchronous version in terms of the asynchronous version transparently. I'm not up to speed with the specifics of this pattern (and whether it is ready for production code yet).

Q. If I am not doing networking, should I still use Boost::Asio?

Should? No. But you may. In general, with c++20 coroutines you will want to use some library like cppcoro or indeed Asio. That's because no user-level library facilities have been standardized yet.

In Asio the interesting bits are:

  1. experimental stuff like channels ( channel and concurrent_channel ), parallel_group, wait_for_{all,one,any}

  2. the general purpose facility coro which has a lot of flexibility. You could see it as the most useful 80% of cppcoro but

    • all in one relatively simple class template:

      1. coro<T> -> simple generator
      2. coro<T(U)> -> generator with input
      3. coro<void, T> task producing a T
    • integrated with Asio executors

This documentation is a pretty decent introduction ¹, especially when you're familiar with concepts from other libraries/languages.

Q. Where do std::async and the senders/receivers proposal fit into all this?

I'm not sure. I seem to remember Chris Kohlhoff wrote that proposal. The concept may be lurking under the channel / deferred abstractions in Asio already.


¹ Hat tip @klemensmorgenstern

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM