C++:unique_ptr 与 auto_ptr,以及 unique_ptr 相对于 auto_ptr 的优点?

问题描述 投票:0回答:1

我不完全理解

unique_ptr
相对于
auto_ptr
的好处,或者我还没有完全相信为什么我们需要使用
unique_ptr

我看到以下差异。

1)

unique_ptr
支持数组,因此
unique_ptr
析构函数为数组调用
delete []
,而
auto_ptr
析构函数仅调用
delete

2) 遇到

std::move()
时,必须使用
unique_ptr
,而不是直接复制。但是
std::move()
能给我们带来什么好处呢?我将尝试如下解释。

auto_ptr <int> p1 (new int);
auto_ptr <int> p2 = p1;    // Now p1 is NULL and p2 exists with value of p1

unique_ptr <int> p1 (new int);
unique_ptr <int> p2 = std::move(p1);    // Now p1 is NULL and p2 exists with value of p1

那么我们将获得什么优势?

3)我在网上看到

unique_ptr
可以用在容器中。但如果我理解正确的话,这并不是
unique_ptr
的伟大之处。容器函数语义发生了变化,因此现在,复制无法在容器函数内部完成。但这是
unique_ptr
的伟大之处吗?既然容器功能都变了,为什么我们不能在容器中使用
auto_ptr
呢?

c++ unique-ptr auto-ptr
1个回答
11
投票

首先,

auto_ptr
有神奇的构造函数,比如
auto_ptr(auto_ptr &other) {...}
,其行为如下:

  • 首先从
    other
    实例复制。
  • 然后空构造
    other
    实例。

现在的编译器支持

std::move(...)
,因此不需要实际上“移动”的“复制式”构造函数,但为了支持旧代码,
auto_ptr
保持不变,而是被弃用(稍后删除)。

unique_ptr
迫使您明确转让所有权,因此它在代码中是可见且清晰的。使用
auto_ptr
,很容易获得所有权的静默转移,并且在阅读代码时,并不总是清楚所有权是否已转移,如果是,则不清楚它是代码作者的意图还是一个错误!当您看到
unique_ptr
std::move
一起使用时,很明显其意图是转移所有权。

unique_ptr
正确支持移动语义,因此它只允许从临时对象和移动对象(即rvalues)进行所有权转移。容器可以检测类型是否“移动感知”并采取适当的行动。
auto_ptr
不知道移动语义,并且会从左值或右值转移所有权,因此容器认为它是一个普通的可复制对象,但它的行为并不像一个对象,因为它在复制时修改了其源。

小心使用时,

auto_ptr
很有用,但很容易误用它并编写危险的代码。是时候让它死去了。
unique_ptr
支持
auto_ptr
可以做的一切,但默认情况下是安全的(你必须更加努力地使用它),并且还具有额外的功能,例如自定义删除器和数组支持。

© www.soinside.com 2019 - 2024. All rights reserved.