shared_ptr 未能推送到向量

Posted

技术标签:

【中文标题】shared_ptr 未能推送到向量【英文标题】:shared_ptr failed to be pushed to vector 【发布时间】:2016-06-29 21:32:51 【问题描述】:

我有 boost shared_ptr 的向量,但是,当我推到本地制作的新 shared_ptr 的末尾时,它会失败。谁能告诉我下面的代码有什么问题?

std::vector<boost::shared_ptr< A > > vecA;

BOOST_FOREACH(const std::string& s, vecStrings)

   boost::shared_ptr<A> pNewA = boost::make_shared<A>(s);
   pNewA->MyString(); //OK
   vecA.push_back(pNewA); //throw error Assertion `px != 0' failed

更新: 好像不是push的问题,不过我用了shared_ptr的引用。

 for(int i=0, n=vecA.size(); i <n; i++)


    //use pA
     boost::shared_ptr& pA = vecA[i];
     vecA.push_back(pA);
    //will core dump at the end of loop because pA changed due to vector enlarge

【问题讨论】:

什么是ApNewA-&gt;MyString() 是什么? 我怀疑Undefined Behaviour。尝试在较小的样本中重现您的问题。逐渐消除错误的来源,直到它消失。 A 只是一个结构体,有一个字符串成员和两个整数成员。 【参考方案1】:

不知道为什么你在那里使用 boost 库(对它们不太熟悉),但共享指针也在标准库内存中

#include <memory>

很可能是共享指针对象的所有权问题。如果使用标准库编写,正确的代码将如下所示:

#include <vector>
#include <memory>

//...

std::vector<std::shared_pointer<A> > vecA;

//version 1
std::shared_ptr<A> pNewA = std::make_shared<A>(s);
pNewA->MyString();
vecA.push_back(std::move(pNewA)); //std::move moves ownership to vector

//or alternativeley
vecA.push_back(std::shared_pointer<A>(new class A(s)));

或类似的东西..

HTH

【讨论】:

std::shared_ptr 有一个复制构造函数,因此在将std::shared_ptr 推入容器时不需要std::move()。另一方面,如果您使用的是std::unique_ptr,那么您将需要std::move(),因为std::unique_ptr 没有复制构造函数,但有一个移动构造函数。无论哪种方式,如果您真的想推送一个新对象,请考虑使用emplace_back() 而不是push_back() 还没有研究 c++14,所以 emplace_back() 对我来说是新的。谢谢! emplace_back() 是在 C++11 中添加的,与 std::shared_ptrstd::make_shared() 相同。 emplace_back 如果您使用移动或复制 ctor,则没有任何好处 我不得不在项目中使用 boost,因为我必须链接到另一个没有 c++11 支持的库。至少我认为 Boost 版本应该与 std 版本没有太大区别?

以上是关于shared_ptr 未能推送到向量的主要内容,如果未能解决你的问题,请参考以下文章

识别已将哪个基类 shared_ptr 传递到超类 shared_ptr 向量中

如何将 shared_ptr 变量推回 C++ 中的 shared_ptr 向量?

抽象类的 shared_ptr 向量到副本向量

向量问题中的 shared_ptr - 迭代和丢失范围 - 获取损坏的数据

为啥我不能在 C++0x 中对 std::shared_ptr 的向量执行 std::copy?

C++ std::array 到 shared_ptr 的向量