为什么boost::asio::io服务被设计成用作参数?



我是c++ asio的初学者,发现io_service的使用方式非常令人困惑。

我对io_service的理解是它是一个任务队列。和python一样,你可以使用:

asyncio.gather(*[task1, task2...])

将你的任务放到这个队列中,然后运行循环。

然而,在c++中,io_service被用作传递给其他事物的参数。

示例如下https://www.boost.org/doc/libs/1_76_0/doc/html/boost_asio/tutorial.html。io_service用作传递给对象或函数的参数,如下所示。它被传递给计时器:

boost::asio::io_context io;
boost::asio::steady_timer t(io, boost::asio::chrono::seconds(5));

boost::asio::io_context io_context;
tcp_server server(io_context);

我的问题是,为什么这样做?将io_service传递给函数或对象,但传递的io_service保存任务,这有什么神奇之处?例如,计时器任务现在在io_service的队列中。

如果我要定义一个自定义函数可能使用opencv读取图像,而不是在asio,定时器套接字等预定义的任务。我应该如何创建接受io_service作为参数的对象或函数?谢谢你的帮助!

在过去的几年中,您实际上可以传递执行器,这比传递对您的服务的引用要好得多。所以,还是那样做吧。

一般来说,这个原则被称为依赖注入,不管具体的接口是什么,你都需要它。

最后,选择自由函数而不是成员操作是一个明显的python风格的选择,这在传统的面向对象编程语言中很少见。例如,鼓励你写

post(executor, task);

不是

executor.post(task);

非常类似于python模式,例如你说str(obj)len(obj)而不是obj.str()obj.len()

注意c++增加了更多的余地,如果任务有关联的执行器,您可以简单地说

post(task);

它的行为相当于post(get_associated_executor(task), task));

查看更多背景:

  • 何时必须通过io_context来boost::asio::spawn?(c++)
  • std::boost::asio::post/dispatch使用哪个io_context ?

最新更新