C++如何同时运行2个boost:asio:io_context



我有两个boost::asio::io_context变量,一个用于我的Raspberry Pi和我的arduino之间的连接,另一个用于Raspberrry Pi和客户端之间通过tcp服务器的连接。我分别测试了两个连接,它们运行得非常好。然而,当我尝试加入他们时,这是行不通的。我知道,通过制作两个io.run,第二个将永远不会被输入,因为程序将卡在第一个中,所以我如何将io.run插入io_context.run((中?

我的主要内容如下:

boost::asio::io_context io_context;
boost::asio::io_context io;
int main{
//create a server object to accept incoming client connections
tcp_server server(io_context);
open_port_arduino();

start = std::chrono::high_resolution_clock::now(); //time_init
//writes to arduino with intervals of 2 seconds
tim.expires_after(boost::asio::chrono::seconds {2});
tim.async_wait(timer_handler);
//reads from arduino
start_read_arduino();
io.run();
io_context.run();
}

要回复您的评论:您不需要第二个io_context。

但是,您可以(另请参阅我们是否需要每个线程多个io_service来实现具有单个接收器和https://theboostcpplibraries.com/boost.asio-scalability)。

一个好处可能是线程隔离:如果在单独的线程上运行单独的上下文,则存在隐式任务序列化。(与多个线程上的单个上下文相比,在多个线程中,任务可能需要手动序列化,例如使用链(。

我所能想象的最直接的事情就是";"修复";它只是简单地将引用传递给所有参与者:

在Coliru上直播

static io_context io;
struct tcp_server {
tcp_server(io_context& ctx) : _ctx(ctx) {}
private:
io_context& _ctx; // REFERENCE
};
int main() {
tcp_server server(io);
// ...

(现场演示按预期打印"计时器回调:成功"(

多线程

如果您的一些IO任务阻塞了相当长的时间,您将需要运行几个线程。在这种情况下,我会将方法转换为将执行器传递给类,并确保它们将其打包为多条:

boost::asio::thread_pool io(2); // two threads
using boost::asio::any_io_executor;
struct tcp_server {
tcp_server(any_io_executor ex) : _ex(make_strand(ex)) {}
private:
any_io_executor _ex;
};

然后

int main() {
//create a server object to accept incoming client connections
tcp_server server(io.get_executor());

同样,Live演示打印";计时器回调:成功;正如预期的那样。

我知道这已经关闭了很长时间,但如果有人想在不深入线程池的情况下实现多线程ioContext,那么像这样简单的东西可以在中工作

boost::asio::io_context ioc1;
boost::asio::io_context ioc2;
/** assign tasks to ioc1 and ioc2 */
std::thread t1([&ioc1](){ioc1.run();});
std::thread t2([&ioc2](){ioc2.run();});
/** do more work on main-thread */
ti.join();
t2.join();

最新更新