std :: unique_ptr析构函数构造函数顺序

时间:2018-07-28 06:16:32

标签: c++ std

我想知道将新的unique_ptr分配给先前的unique_ptr时会发生什么。在下面的代码中:

double[] a, b, c;
c = Arrays.copyOf((b = Arrays.copyOf((a = new double[10]), a.length)), b.length);

我希望第二次分配新的std :: unique_ptr进行测试时,首先调用my_class的析构函数,然后调用它的构造函数。 我期望的是错误的吗? 但是当我调试代码时,我看到的是相反的。首先调用my_class的构造函数,然后调用其析构函数。

2 个答案:

答案 0 :(得分:6)

在先前实例的析构函数之前调用构造函数的原因是,因为您要将new my_class()作为参数传递给unique_ptr的构造函数。首先对参数进行求值,构造一个新的unique_ptr实例,该实例获取新创建对象的所有权,然后将该新的unique_ptr实例分配给旧对象。

结果是,拥有所有权的旧unique_ptr的my_class对象将被释放并销毁,从而调用my_class析构函数。

它实际上与您编写的内容相同:

my_class* temp = new my_class;
test = std::unque_ptr<my_class>(std::move(temp));

在这里可以直接看到新对象的构造。

答案 1 :(得分:4)

来自cppreference

  

unique_ptr& operator=( unique_ptr&& r ) noexcept;(1)
  template< class> U, class E > unique_ptr& operator=( unique_ptr<U,E>&& r ) noexcept;   (1)

     

将所有权从r转移到*this,就像通过调用   reset(r.release()),然后分配来自get_deleter()的   std::forward<E>(r.get_deleter())

如您所见,reset在前一个指针上被调用,它执行以下操作:

  
      
  1. 保存当前指针old_ptr = current_ptr的副本
  2.   
  3. 使用参数current_ptr = ptr覆盖当前指针
  4.   
  5. 如果旧指针为非空,则删除先前管理的对象   if(old_ptr != nullptr) get_deleter()(old_ptr)
  6.