我正在使用C++11 进行试验,并编写了一个小玩具示例,以查看shared_ptr
调用. 作为基础架构,我使用 llvm/clang 3.0 以及 XCode4 中的 llvm std c++ 库。make_shared
make_shared
class Object
{
public:
Object(const string& str)
{
cout << "Constructor " << str << endl;
}
Object()
{
cout << "Default constructor" << endl;
}
~Object()
{
cout << "Destructor" << endl;
}
Object(const Object& rhs)
{
cout << "Copy constructor..." << endl;
}
};
void make_shared_example()
{
cout << "Create smart_ptr using make_shared..." << endl;
auto ptr_res1 = make_shared<Object>("make_shared");
cout << "Create smart_ptr using make_shared: done." << endl;
cout << "Create smart_ptr using new..." << endl;
shared_ptr<Object> ptr_res2(new Object("new"));
cout << "Create smart_ptr using new: done." << endl;
}
现在看看输出,请:
使用 make_shared 创建 smart_ptr...
构造函数 make_shared
复制构造函数...
复制构造函数...
析构函数
析构函数
使用 make_shared 创建 smart_ptr:完成。
使用新创建 smart_ptr...
构造函数新
使用 new: done 创建 smart_ptr。
析构函数
析构函数
似乎make_shared
调用了复制构造函数两次。如果我为Object
使用常规分配内存,则new
不会发生这种情况,只会Object
构造一个。
我想知道的是以下内容。我听说这make_shared
应该比使用new
( 1 , 2 )更有效。一个原因是因为make_shared
将引用计数与要管理的对象一起分配在同一块内存中。好的,我明白了。这当然比两个单独的分配操作更有效。
相反,我不明白为什么这必须伴随着两次调用Object
. 因此,我不相信在每种make_shared
情况下都比使用分配更有效。我在这里错了吗?好吧,可以实现一个移动构造函数,但我仍然不确定这是否比仅通过分配更有效。至少不是在所有情况下。如果复制比为引用计数器分配内存更便宜,那将是正确的。但是-internal 引用计数器可以使用几个原始数据类型来实现,对吧?new
Object
Object
new
Object
shared_ptr
尽管概述了复制开销,您能否帮助并解释为什么make_shared
在效率方面要走的路?