【问题标题】:Differences when using shared_ptr and unique_ptr to point to an array?使用 shared_ptr 和 unique_ptr 指向数组时的区别?
【发布时间】:2019-02-07 08:21:33
【问题描述】:

在 C++11 中,我刚刚发现 shared_ptrunique_ptr 在用于分配数组时看起来有些区别。如果我发现的内容正确,我想得到确认。

我必须将<int []> 用于unique_ptr,但<int> 仅用于shared_ptr

unique_ptr<int []> myUniquePtr = unique_ptr<int[]> ( new int[100]);

shared_ptr<int> mySharedPtr = shared_ptr<int>( new int[100]);

对于unique_ptr,我不需要为指向数组的指针重载delete functor/lambda func:

unique_ptr<int []> myUniquePtr = unique_ptr<int[]> ( new int[100]); //should be good enough

但我会为shared_ptr

shared_ptr< int> mySharedPtr = shared_ptr<int> ( new int [100], [](const int* p){delete [] p;});

要通过智能指针访问数组中的元素,unique_ptr 可以使用常规方式[index],但shared_ptr 不能这样做:

myUniquePtr[10] = 100; // should be OK

但我需要

mySharedPtr.get()[10] = 100;

您能否确认以上陈述是否正确?在 C++14 中会有什么不同吗?

【问题讨论】:

  • uinque_ptr 具有对数组类型的专门化,因此它可以在不提供删除器的情况下判断是否需要使用deletedelete[]。但是,如果您需要分配一个数组并拥有相应的访问器,您可能希望使用std::vectorstd::array
  • 您可能需要查找make_uniquemake_shared

标签: c++ c++11 shared-ptr unique-ptr


【解决方案1】:

可以通过std::unique_ptr 的特化template &lt;class T, class Deleter&gt; class unique_ptr&lt;T[], Deleter&gt; 来解释不同的行为。当使用数组类型而不是标量类型时,这种特化允许不同的行为。

如果您查看https://en.cppreference.com/w/cpp/memory/unique_ptr,您还可以看到只有数组变体实现了operator [],这允许您进行3中描述的访问。

如果您查看https://de.cppreference.com/w/cpp/memory/shared_ptr 的文档,您会发现T[]std::shared_ptr 的情况下没有特殊处理。因此,您需要先检索原始指针,然后才能使用“标准”数组访问。此外,它无法决定何时使用delete,何时使用delete[],因此如果不传递标准删除器可以删除的对象,则需要提供删除器。

Afaik,在 C++14 中这种行为没有变化。

【讨论】:

  • C++17 添加了[] 重载,用于使用 shared_ptr 访问数组
猜你喜欢
  • 2011-10-16
  • 1970-01-01
  • 1970-01-01
  • 2013-08-24
  • 1970-01-01
  • 2011-04-19
  • 1970-01-01
  • 2013-04-16
  • 1970-01-01
相关资源
最近更新 更多