[英]Is it safe to use boost::asio::strand in this way?
Said I have a worker class 说我有一个工人阶级
class MyWorker : public std::enable_shared_from_this<MyWorker> {
public:
MyWorker(boost::asio::io_service& ioService) : strand_(ioService) {}
void Work(int n) {
strand_.post([weak_this = weak_from_this(), n]() {
printf("work %d run from strand\n", n);
if (auto ptr = weak_this.lock()) ptr->DoWork(n);
});
}
void DoWork(int n) {
n_ = n;
printf("work %d done\n", n);
}
private:
boost::asio::io_service::strand strand_;
int n_;
};
Anyone can post works to a worker object, and it will be en-queued and do work in sequence. 任何人都可以将作品发布到工作者对象,它将被排队并按顺序工作。 When I want to stop a worker object, I can just un-reference shared _ptr. 当我想要停止一个worker对象时,我可以取消引用shared _ptr。 Pending work will not call into object (protected by weak_ptr) 待处理的工作不会调用对象(受weak_ptr保护)
Here is example scenario 这是示例场景
int main() {
boost::asio::io_service ioService;
auto worker = std::make_shared<MyWorker>(ioService);
ioService.post([] () { printf("other work 1\n"); });
worker->Work(1);
ioService.post([] () { printf("other work 2\n"); });
worker->Work(2);
worker.reset(); // <- strand_ destroyed after this line
ioService.run();
return 0;
}
This exmaple can run without crash. 这个例子可以在没有崩溃的情况下运行。 The output is 输出是
other work 1
work 1 run from strand
other work 2
work 2 run from strand
No "work 1 done", "work 2 done" which is expected. 没有“工作1完成”,“工作2完成”这是预期的。
But at the time I called io_service::run(), strand is already destroyed. 但是在我调用io_service :: run()时,strand已经被销毁了。 Is this safe? 这样安全吗? Or something undefined behavior may happened? 或者可能发生一些未定义的行为?
Oh, I almost forgot about this question since my comment: 哦,自从我的评论以来,我差点忘了这个问题:
Looks fine to me (much easier to see if you imagine MyWorker::Work as a free function). 对我来说很好看(如果你想象MyWorker :: Work作为免费功能,会更容易看到)。 It does assume that it's okay to have wrapped handlers even after the strand object is destroyed. 它确实假设即使在strand对象被销毁之后也可以包装处理程序。 I think that is okay, but I'd need to check. 我认为没关系,但我需要检查一下。
I did have a look at the implementation and indeed the implementation of the strand service is such that it is safe to have handlers associated with them after destructing the strand
instance. 我确实看过了实现,实际上,strand服务的实现是这样的,即在破坏strand
实例之后让处理程序与它们相关联是安全的。
That makes your code fine. 这使你的代码很好。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.