创建shared_ptr时,类析构函数被调用两次

时间:2017-01-10 01:10:22

标签: c++

我在向我的类创建共享ptr时遇到类析构函数被调用两次的问题。

我试图创建一个对象向量,每个对象都有一个构造函数和一个析构函数。

当我打电话时,如:

std::vector<std::shared_ptr<ServoController>>  servos;
bool CreateServo(int id)
{
    std::shared_ptr<ServoController> servo = std::make_shared<ServoController>(ServoController(id));
    servos.push_back(servo);
}

调用ServoController的构造函数,然后立即调用Destructor for ServoController,之后甚至调用push_back函数。

然后,当我关闭我的应用程序时,再次调用ServoController的析构函数。但到目前为止,构造函数只被称为一次(我在向量中只有一个对象)。至少它不应该让构造函数再次运行吗?

我有没有办法制作我的类的向量,对于向量中的每个对象,构造函数应该被调用一次,并且当从向量中移除对象或向量时,应该调用析构函数一次销毁?

谢谢, -D

1 个答案:

答案 0 :(得分:12)

您正在使用此调用创建一个临时对象,这是导致第一个(意外)析构函数调用的原因。

app figures
asana
basecamp3
bitly
blogger
box
buffer
campfire
chatter
disqus
docusign
dropbox
Dynamics 365 for operations
dynamics 365
facebook
GitHub
Google Calendar
Google Contacts 
Google Drive
Google Sheets
GotoMeeting
GotoTraining
Harvest

事件的顺序是:

  • std::make_shared<ServoController>(ServoController(id)); 创建一个新的临时对象,该对象作为参数传递给ServoController(id)
  • std::make_shared然后将临时对象转发给std::make_shared<ServoController> 复制构造函数(可能不是您想要的)。这就是为什么你的主构造函数只被调用一次。
  • 这会在堆上创建一个新对象(由ServoController管理),它是您创建的临时副本。
  • 然后立即销毁临时对象,这是第一次调用析构函数。

你真正想要的是:

shared_ptr

std::make_shared<ServoController>(id); 将其参数直接转发给其模板参数的构造函数。你不需要额外的构造函数调用。