2013-06-13 2 views
1

Я хочу изменить default_deleter для std::unique_ptr. Это довольно легко достичь, но есть один неудобно - я должен объявить переменные, используя 2 параметра шаблона вместо одного, что-то вроде этого:Замена делетира для std :: unique_ptr

std::unique_ptr<MyType, MyDeleter<MyType>> myVar; 

Как вы можете видеть, декларация долго и у меня есть ощущение, Я могу использовать более короткую версию, но я не знаю, как :)

Можно ли объявить какой-то MyUniquePtr<T>, который будет таким же, как std::unique_ptr<T, MyDeleter<T>>?

EDIT: Matthieu M. уже ответил, но, к сожалению, я не могу использовать эту функцию в Visual Studio, поскольку она не реализована. Есть ли другой способ добиться такого поведения?

ответ

8

На самом деле это, используя шаблон псевдонимы:

template <typename T> 
using MyUniquePtr = std::unique_ptr<T, MyDeleter<T>>; 
+1

Очень приятная функция, но я не могу использовать ее, потому что она не реализована в Visual Studio :( – Felics

+0

В этом случае тег C++ 11 довольно спорный, так как реализация Microsoft нигде не завершена. это, может быть, они будут реализовывать эту функцию в двух версиях с этого момента.; -P –

3

Если ваш компилятор не делают псевдонимы шаблона еще, вот C++ 03 идиом:

template <typename T> 
struct MyUniquePtr { 
    typedef std::unique_ptr<T, MyDeleter<T> > type; 
}; 

MyUniquePtr<MyType>::type var; 

Установка является уродливее, но в результате использование почти так же коротко: вам просто нужно добавить ::type.

+0

Перед чем? – aschepler

0

Другой способ, соответствующий C++ 03, является подклассом, который, к сожалению, требует, чтобы вы воспроизводили конструкторы. (Это можно сделать проще, если ваш компилятор поддерживает VARIADIC аргументов шаблона, которые могут быть в случае текущего MSVC.)

template <class T> 
class MyUniquePtr : public std::unique_ptr< T, MyDeleter<T> > { 
public: 
    MyUniquePtr(args...) : std::unique_ptr< T, MyDeleter<T> >(args...) { } 
}; 
3

нужна ли ваша Deleter быть шаблонным от типа объекта удаляется, или достаточно ли для того, чтобы оператор вызова функции был настроен на тип удаляемого объекта?

Вместо:

template<typename T> 
struct MyDeleter 
{ 
    void operator()(T* p) const { /* ... */ } 
}; 

Вы можете написать:

struct MyDeleter 
{ 
    template<typename T> 
    void operator()(T* p) const { /* ... */ } 
}; 

Это, конечно, зависит от того, в каком состоянии MyDeleter должен поддерживать.

0

Возможно, вам стоит подумать о том, чтобы написать собственную версию функции стиля make_unique, а не специально для вашей стратегии выделения/удаления. Это также имеет то преимущество, что вы можете выполнять любое специализированное приобретение/распределение ресурсов безопасным способом. Затем вы можете объявить свой уникальный_ptr как автоматический и позволить вам делать вывод о вычете.

Смежные вопросы