c++ - 为什么不允许使用 `make_unique<T[N]>`?

标签 c++ language-lawyer unique-ptr c++14

假设命名空间 std贯穿始终。

C++14 委员会草案 N3690 定义 std::make_unique因此:

[n3690: 20.9.1.4]: unique_ptr creation    [unique.ptr.create]

template <class T, class... Args> unique_ptr<T> make_unique(Args&&... args);

1 Remarks: This function shall not participate in overload resolution unless T is not an array.
2 Returns: unique_ptr<T>(new T(std::forward<Args>(args)...)).

template <class T> unique_ptr<T> make_unique(size_t n);

3 Remarks: This function shall not participate in overload resolution unless T is an array of unknown bound.
4 Returns: unique_ptr<T>(new typename remove_extent<T>::type[n]()).

template <class T, class... Args> unspecified make_unique(Args&&...) = delete;

5 Remarks: This function shall not participate in overload resolution unless T is an array of known bound.

现在,在我看来,这就像泥巴一样清晰,我认为它需要更多的阐述。但是,除了这篇社论评论,我相信我已经解码了每个变体的含义:

  1. template <class T, class... Args> unique_ptr<T> make_unique(Args&&... args);

    你的沼泽标准make_unique对于非数组类型。据推测,“备注”表示某种形式的静态断言或 SFINAE 技巧是为了防止模板在 T 时成功实例化。是数组类型。

    在高层次上,将其视为等同于 T* ptr = new T(args); 的智能指针.

  2. template <class T> unique_ptr<T> make_unique(size_t n);

    数组类型的变体。创建 n 的动态分配数组× Ts , 并将其返回包装在 unique_ptr<T[]> 中.

    在高层次上,将其视为等同于 T* ptr = new T[n]; 的智能指针.

  3. template <class T, class... Args> unspecified make_unique(Args&&...)

    不允许。 “未指定”可能是 unique_ptr<T[N]> .

    否则,智能指针将等同于无效 T[N]* ptr = new (keep_the_dimension_please) (the_dimension_is_constexpr) T[N]; 之类的东西.

首先,我说的对吗?如果是这样,第三个函数是怎么回事?

  • 如果它不允许程序员在为每个元素提供构造函数参数的同时尝试动态分配数组(就像 new int[5](args) 是不可能的),那么这已经被第一个函数不能被覆盖的事实所涵盖为数组类型实例化,不是吗?

  • 如果它的存在是为了防止在语言中添加像 T[N]* ptr = new T[N] 这样的结构(其中 N 是一些 constexpr )那么,为什么? unique_ptr<T[N]> 不是完全有可能吗?存在包装动态分配的 N block × T年代?如果委员会已经竭尽全力禁止使用 make_unique 创建它,这会是一件坏事吗? ?

为什么是make_unique<T[N]>不允许?

最佳答案

引自 the original proposal :

T[N]

As of N3485, unique_ptr doesn't provide a partial specialization for T[N]. However, users will be strongly tempted to write make_unique<T[N]>(). This is a no-win scenario. Returning unique_ptr<T[N]> would select the primary template for single objects, which is bizarre. Returning unique_ptr<T[]> would be an exception to the otherwise ironclad rule that make_unique<something>() returns unique_ptr<something>. Therefore, this proposal makes T[N] ill-formed here, allowing implementations to emit helpful static_assert messages.

提案的作者 Stephan T. Lavavej 在 this video on Core C++ 中说明了这种情况。 (由 chris 提供),从 1:01:10 分钟开始(或多或少)。

关于c++ - 为什么不允许使用 `make_unique<T[N]>`?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16596950/

相关文章:

c++ - unique_ptr 无法初始化

c++ - 基于unique_ptr参数指针类型的重载函数

C++11 - 复制指向抽象类型的智能指针的构造?

C++将对象从文件复制到数组

c++ - 当编译器看不到可以完成转换的可能类型时,是否允许编译器优化 volatile 指针的 dynamic_cast?

c++ - 如何使用可变参数模板处理模板特化?

c++ - 关于char的签名问题

c++ - 为什么 C 基本类型的标识符具有多个关键字

c++ - 如何以平台中立的方式确定架构?

C++ 格式化日期