[英]boost shared_ptr: difference between operator= and reset?
下面的两段代码之间有什么区别吗? 他们中的任何一个比另一个更可取吗?
运算符=
boost::shared_ptr<Blah> foo; // foo.ptr should be NULL
foo = boost::shared_ptr<Blah>(new Blah()); // Involves creation and copy of a shared_ptr?
重启
boost::shared_ptr<Blah> foo; // foo.ptr should be NULL
foo.reset(new Blah()); // foo.ptr should point now to a new Blah object
注意:我需要定义shared_ptr,然后将其设置在另一行中,因为我在一段代码中使用它,例如:
boost::shared_ptr<Blah> foo;
try
{
foo.reset...
}
foo...
operator=
将shared_ptr
分配给shared_ptr
,而reset
使shared_ptr
拥有指针的所有权。 因此,您发布的示例之间基本上没有区别。 就是说,您不应该选择其中任何一个,而只需使用make_shared
:
foo = boost::make_shared<Blah>();
另外,如果可能的话,可以通过将try-catch块包装在一个单独的函数中来避免在不进行初始化的情况下声明shared_ptr
,该函数只需将shared_ptr
返回到新创建的对象:
boost::shared_ptr<Blah> createBlah() {
try {
// do stuff
return newBlah;
}
catch ...
}
operator=
将另一个shared_ptr
作为参数,从而创建另一个副本(并增加引用计数),而reset()
获取一个指针和一个可选的删除器,从而实际上在当前副本的顶部创建一个新的shared_ptr。
reset等效于(并且可能实现为)
void reset(T p, D d)
{
shared_ptr shared(p,d);
swap( shared );
}
operator=
可能实现为:
shared_ptr& operator=( shared_ptr const& other )
{
shared_ptr shared(other);
swap(other);
return *this;
}
这两个函数的相似之处在于,它们释放对它们已经包含的内容的控制(如果有的话),而是管理一个不同的指针。
foo.reset(p)
定义为与shared_ptr(p).swap(foo)
等效。
分配在逻辑上等效于复制和交换,并且可能以这种方式实现。 所以foo = shared_ptr(p);
等效于foo.swap(shared_ptr(p))
。 如果编译器的日子很不好,可能在其中有一个额外的副本。
因此,在您提供的示例中,我认为它们之间没有太多选择。 可能还有其他情况很重要。 但是reset与模板构造函数所做的相同,是基于模板的静态类型p
的基于模板的捕获,因此就获得正确的删除器而言,您已经了解了。
分配的主要用途是当您要复制先前存在的shared_ptr
,以共享同一对象的所有权时。 当然,从临时分配时也可以正常工作,如果您查看不同的reset
重载,它们将反映不同的构造函数。 因此,我怀疑您可以通过任何一种方式实现相同的目标。
赋值运算符从现有对象创建一个新的共享对象,从而增加引用计数
CSharedObj& CSharedObj::operator=(CSharedObj& r) noexcept
{
if(*this != r){
//detach from the previous ownership
if(0 == dec()) delete m_pControlObj;
//attach to the new control object and increment the reference count
r.inc();
m_pControlObj = r.m_pControlObj;
}
return *this;
}
而reset调用不会创建新的共享库,而是创建新的所有权-附加到新的基础pointee(通过控制对象)
void CSharedObj::reset(Ptr pointee) noexcept
{
//check if this is a last reference-detach from the previous ownership
if(0==dec()) delete m_pControlObj;
// create the ownership over the new pointee (refCnt = 1)
m_pControlObj = new (std::nothrow) CControlObj(pointee);
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.