繁体   English   中英

以这种方式使用boost :: asio :: strand是否安全?

[英]Is it safe to use boost::asio::strand in this way?

说我有一个工人阶级

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_;
};

任何人都可以将作品发布到工作者对象,它将被排队并按顺序工作。 当我想要停止一个worker对象时,我可以取消引用shared _ptr。 待处理的工作不会调用对象(受weak_ptr保护)

这是示例场景

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;
}

这个例子可以在没有崩溃的情况下运行。 输出是

other work 1
work 1 run from strand
other work 2
work 2 run from strand

没有“工作1完成”,“工作2完成”这是预期的。

但是在我调用io_service :: run()时,strand已经被销毁了。 这样安全吗? 或者可能发生一些未定义的行为?

哦,自从我的评论以来,我差点忘了这个问题:

对我来说很好看(如果你想象MyWorker :: Work作为免费功能,会更容易看到)。 它确实假设即使在strand对象被销毁之后也可以包装处理程序。 我认为没关系,但我需要检查一下。

我确实看过了实现,实际上,strand服务的实现是这样的,即在破坏strand实例之后让处理程序与它们相关联是安全的。

这使你的代码很好。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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