如何为std :: unique_ptr创建有效的C ++别名模板

Dom*_*tos 5 c++ arrays templates unique-ptr c++11

我想为此提供一个别名模板,std::unique_ptr以提供自己的删除功能。

unique_ptr 具有标量和数组实现,它们的定义如下:

template <class T, class D = default_delete<T>>
class unique_ptr // scalar

template <class T, class D>
class unique_ptr<T[], D> // array
Run Code Online (Sandbox Code Playgroud)

我在尝试覆盖的标量和数组版本时遇到麻烦unique_ptr。为一个版本创建别名很容易,如下所示:

template<class T>
struct Deleter {
    void operator()(T* ptr) { delete ptr; }
};

template<class T>
using my_unique_ptr = std::unique_ptr<T Deleter<T>>;
Run Code Online (Sandbox Code Playgroud)

但是,当我尝试添加第二个别名时,如下所示:

template<class T>
struct ArrayDeleter {
    void operator()(T* ptr) { delete [] ptr; }
};
template<class T>
using my_unique_ptr = std::unique_ptr<T[], ArrayDeleter<T>>;
Run Code Online (Sandbox Code Playgroud)

...由于“ my_unique_ptr”含糊不清,我最终遇到编译器错误。

我的问题是:如何创建一个既适用于数组又适用于标量版本的别名unique_ptr

Yak*_*ont 4

您似乎正在尝试专门化using声明。你不可以。

template<class T>
struct my_unique_ptr_helper {
  using type = std::unique_ptr<T, Deleter<T>>;
};
template<class T>
struct my_unique_ptr_helper<T[]> {
  using type = std::unique_ptr<T[], ArrayDeleter<T>>;
};

template<class T>
using my_unique_ptr = typename my_unique_ptr_helper<T>::type;
Run Code Online (Sandbox Code Playgroud)

现在这有一个缺点,因为它完全阻止了演绎。

我们可以通过将专业转移到其他地方来解决这个问题。

template<class T>
struct Deleter {
  void operator()(T* ptr) const {
    delete ptr;
  }
};
template<class T>
struct ArrayDeleter {
  void operator()(T* ptr) const {
    delete[] ptr;
  }
};
template<class T>
struct Deleter<T[]>:ArrayDeleter<T> {}; // inheritance
Run Code Online (Sandbox Code Playgroud)

现在:

template<class T>
using my_unique_ptr = std::unique_ptr<T, Deleter<T>>;
Run Code Online (Sandbox Code Playgroud)

更简单,并且可以允许更多的扣除T

当然,这一切都是毫无意义的,但我认为你的 realDeleterstd::default_delete.