Boost 智能指针和非 POD 类型 (C++)
在使用智能指针进行练习并了解它们如何通过 RAII 防止内存泄漏并帮助内存管理时,我做了以下事情:
#include <boost/shared_ptr.hpp>
#include <vector>
#include <iostream>
using std::cout;
using boost::shared_ptr;
class myobj {
public:
shared_ptr<int> a;
myobj() {
shared_ptr<int> b(new int[50]);
a = b;
}
~myobj() {}
};
typedef boost::shared_ptr<myobj> myobj_ptr;
int main() {
for (unsigned int i=0; i < 5000000; i++) {
myobj *foo = new myobj();
myobj *bar = new myobj();
myobj_ptr bar_ptr(bar);
bar_ptr = myobj_ptr(foo);
bar = foo;
}
return 0;
}
有没有什么方法可以实现与此类似的功能(希望我的目标能在“伪”代码中实现):
a = new int[50];
我可以从 Boost shared_ptr.hpp 文件本身看出为什么这不起作用,但我不明白为什么这不起作用:
shared_ptr<int> a;
int *b;
myobj() {
b = new int[50];
boost::detail::sp_enable_shared_from_this( a, b, b );
}
它返回了这个错误:
warning: cannot pass objects of non-POD type ‘class boost::shared_ptr<int>’ through ‘...’; call will abort at runtime
我不太明白。
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
首先,boost::detail 中的任何内容都是实现细节。除非您正在开发将成为 boost 本身一部分的代码,否则不要碰它。
其次,boost::shared_ptr 不能直接包装数组。这是因为 C++ 中的数组必须用
delete []
删除,而boost::shared_ptr
则用delete
删除。使用boost::shared_array
相反,或者可能是boost::shared_ptr
到std::vector
。如果您确实必须将shared_ptr
与数组一起使用,则必须使用自定义删除器创建它:但是,实际上请不要这样做。使用
shared_array
或shared_ptr 。 >
。至于为什么你不能这样做:
这是因为让某些东西变得太容易成为shared_ptr是危险的 - 请记住,如果你将某些东西变成shared_ptr两次,你最终会双重释放它。所以shared_ptrs只会通过它们的构造函数获取原始指针。如果您确实想用原始指针覆盖 shared_ptr,有一种方法:
创建一个新指针,然后将其与
a
交换。然后临时智能指针(带有a
的旧值)被释放。First, anything in
boost::detail
is an implementation detail. Don't touch it unless you're developing code that will be a part of boost itself.Second,
boost::shared_ptr
is not directly capable of wrapping arrays. This is because arrays in C++ must be deleted withdelete []
, whileboost::shared_ptr
deletes withdelete
instead. Useboost::shared_array
instead, or perhaps aboost::shared_ptr
to astd::vector
. If you really must use ashared_ptr
with an array, you must create it using a custom deleter:Please don't actually do this, however. Use a
shared_array<int>
or ashared_ptr<vector<int> >
.As for why you can't just do:
This is because it would be dangerous to make it too easy to make something a shared_ptr - remember, if you make something a shared_ptr twice, you'll end up double-freeing it. So shared_ptrs will only take raw pointers through their constructor. If you really want to overwrite a shared_ptr with a raw pointer, here's one way:
This creates a new pointer, then swaps it with
a
. The temporary smart pointer (witha
's old value) is then freed.您无法将使用
new int[50]
分配的内容分配给shared_ptr
,除非您还提供执行delete[]
的自定义删除器代码>而不是<代码>删除。enable_shared_from_this
旨在为类类型添加检索所属共享指针的功能,您刚刚从detail
命名空间中提取了一些内容。这不是为直接使用而设计的。它被设计成这样使用。最简单的数组管理容器是
std::vector
,而不是shared_ptr
。You can't assign something allocated with
new int[50]
to ashared_ptr<int>
unless you also supply a custom deleter that performsdelete[]
instead ofdelete
.enable_shared_from_this
is designed to add the ability for class types to retrieve an owning shared pointer, you've just pulled something out of thedetail
namespace. This isn't designed to be used directly. It's designed to be used like this.The simplest managing container for arrays would be
std::vector<int>
, notshared_ptr
.对于初学者来说,您调用的函数位于
detail
命名空间中,这意味着它可能不适合直接调用。这可能与你的问题有关。至于您收到的特定错误,该错误通常意味着您尝试调用传入非 POD 参数的 varargs 函数。在本例中,这是因为
boost::shared_ptr
不是 POD 类型。我认为这与使用数组和原始指针无关;我认为你只是用错误的参数调用了错误的函数。您是想使用boost::shared_from_this
吗?For starters, the function you're calling is in the
detail
namespace, meaning that it's probably not meant to be invoked directly. That may have something to do with your problem.As for the particular error you're getting, that error usually means that you tried to call a varargs function passing in a non-POD argument. In this case, that's because
boost::shared_ptr<int>
isn't a POD type. I think this has nothing to do with using arrays versus raw pointers; I think you're just calling the wrong function with the wrong arguments. Did you mean to useboost::shared_from_this
?