你如何正确使用boost :: make_shared_ptr?

App*_*ood 2 c++ boost boost-asio visual-studio-2008 visual-c++

这个简单的例子无法在VS2K8中编译:

    io_service io2;
    shared_ptr<asio::deadline_timer> dt(make_shared<asio::deadline_timer>(io2, posix_time::seconds(20)));
Run Code Online (Sandbox Code Playgroud)

就像这个一样:

shared_ptr<asio::deadline_timer> dt = make_shared<asio::deadline_timer>(io2);
Run Code Online (Sandbox Code Playgroud)

错误是:

错误C2664:'boost :: asio :: basic_deadline_timer :: basic_deadline_timer(boost :: asio :: io_service&,const boost :: posix_time :: ptime&)':无法从'const boost :: asio :: io_service转换参数1 'to'boost :: asio :: io_service&'

GMa*_*ckG 7

问题是asio::deadline_timer有一个构造函数需要对服务的非const引用.但是,当你使用make_shared它的参数时const.也就是说,这部分make_shared问题是:

template< class T, class A1 > // service is passed by const-reference
boost::shared_ptr< T > make_shared( A1 const & a1 )
{
    // ...

    ::new( pv ) T( a1 ); // but the constructor requires a non-const reference

    // ...
}
Run Code Online (Sandbox Code Playgroud)

您可以做的是将服务包装成a reference_wrapper,使用ref:

#include <boost/ref.hpp>

asio::io_service io1;
shared_ptr<asio::deadline_timer> dt = // pass a "reference"
    make_shared<asio::deadline_timer>(boost::ref(io1));
Run Code Online (Sandbox Code Playgroud)

这将获取您的实例,并将其放入一个可以隐式转换为对您的isntance的引用的对象.然后,您基本上传递了一个对象,该对象表示对您的实例的非const引用.

这是有效的,因为它reference_wrapper确实存储了指向您的实例的指针.因此它可以在仍然存在的情况下返回指针解除引用const.