C++ 我可以为局部变量创建boost::shared_ptr吗?
我有一些方法引用给定对象,还有一些方法引用C++ 我可以为局部变量创建boost::shared_ptr吗?,c++,boost,shared-ptr,C++,Boost,Shared Ptr,我有一些方法引用给定对象,还有一些方法引用boost::shared\u ptr。到目前为止,在我的测试方法中,我创建了一个指向其中一个对象的shared_ptr,并将*ptr传递给期望引用的方法。是否可以反过来做,例如在堆栈上创建一个本地对象,然后以安全的方式创建指向该对象的共享指针,以获得使用传统指针的&obj操作符的直接替代方法 #包括 #include <boost/shared_ptr.hpp> void null_deleter(int *) {} int main(
boost::shared\u ptr
。到目前为止,在我的测试方法中,我创建了一个指向其中一个对象的shared_ptr
,并将*ptr
传递给期望引用的方法。是否可以反过来做,例如在堆栈上创建一个本地对象,然后以安全的方式创建指向该对象的共享指针,以获得使用传统指针的&obj
操作符的直接替代方法 #包括
#include <boost/shared_ptr.hpp>
void null_deleter(int *)
{}
int main()
{
int i = 0;
boost::shared_ptr<int> p(&i, &null_deleter);
}
无效无效删除器(int*)
{}
int main()
{
int i=0;
boost::shared_ptr p(&i,&null_deleter);
}
您可以在表单的构造函数中传递适当的删除程序:
template<class Y, class D> shared_ptr(Y * p, D d);
然后,您可以使用它来构造:
boost::shared_ptr<Foo> f(&obj, no_op<Foo>);
boost::shared_ptr f(&obj,no_op);
如果您发现需要此功能,那么您的代码可能存在严重错误
如果函数采用共享指针,那应该是因为它们需要延长对象的生存期。如果它们不需要延长对象的生存期,则应该使用引用
根据您所做的,它们无法延长对象的生命周期。如果他们需要,或者不能,他们可能会通过您传递给他们的共享指针的副本访问超出范围的对象。轰
这可能有点道理。它们可能需要延长寿命,但您将确保对象的有效期超过它们可能需要延长的最长时间。但我还是强烈建议不要这样做。它非常脆弱,使您调用的所有代码都完全依赖于调用代码的行为。您可以使用c++11 lambda函数:
template <typename T>
void no_op(T*) {}
boost::shared_ptr<Foo> f(&obj, \[ ](Foo*){});
boost::shared\u ptr f(&obj,\[](Foo*){});
您可以在构造函数中传递null\u deleter
#include <boost/shared_ptr.hpp>
#include <boost/core/null_deleter.hpp>
int main()
{
int a = 0;
boost::shared_ptr<int> pi(&a, boost::null_deleter());
}
请记住,这些方法可能希望指针在返回后仍保持活动状态。如果没有,它们应该使用
T&
。只要没有任何东西复制或存储该指针,并且在函数退出后没有任何东西引用该对象。如果有人希望使用指针而不是引用,这可能是有原因的-请确保传递此指针的所有函数都不希望对象在函数退出后仍然存在。@mAlters,这是一种测试方法,因此一旦此方法完成,所有内容都将被清除。不过你的观点是正确的+1如@IgorR的回答中所述,这是一种更通用的方法来声明一个null\u deleter
。@g-makulik嗯,一种更通用的方法如下:-)struct null\u deleter{void operator()(void const*)const{}代码>可能有些情况下您需要执行s.th。这样,如果您有其他接口(可能超出您的控制范围),它们希望显式地使用shared_ptr
s而不是带有指针行为的模板化参数+1不过,总的来说,我同意。@g-makulik:问题是,如果这些接口期望共享\u ptr
,它们几乎肯定也期望能够延长对象的生命周期。否则,这些接口可能会被破坏。(当然,考虑到我们必须与OP合作的现实,做OP想要做的事情可能比修复它们要好。)
#include <boost/shared_ptr.hpp>
#include <boost/core/null_deleter.hpp>
class Y
{
public:
void tryUse()
{
std::cout << "attempt to use :"<< (uintptr_t)(void*)this<< std::endl;
}
~Y()
{
std::cout << "destructor: "<< (uintptr_t)(void*)this<< std::endl;
}
};
struct Y_user
{
boost::shared_ptr<Y> p;
~Y_user()
{
std::cout << "Y_user destructor: "<< (uintptr_t)(void*)this<< std::endl;
if (p.get())
p->tryUse();
}
};
int main()
{
{
Y_user yu;
Y y;
boost::shared_ptr<Y> p (&y, boost::null_deleter() );
yu.p = p;
}
}
destructor: 140737179995232
Y_user destructor: 140737179995264
attempt to use :140737179995232