Мета-программирование шаблона C ++: Наследование от параметра шаблона шаблона - PullRequest
0 голосов
/ 01 июня 2018
#include <type_traits>

template <typename T1, typename T2, typename is_allocated>
struct mutable_storage {};

template <
    template<typename, typename, typename> class storage_t,
    typename T2           = void,
    typename is_allocated = std::false_type
>
class Buffer : storage_t<Buffer<storage_t,void,void>, T2, is_allocated>
{};



int main() {
    typedef Buffer<mutable_storage> example_buffer;
}

Этот код компилируется (по крайней мере, с использованием компилятора GNU GCC, следующего за C ++ 14).Однако мне не нравится используемый синтаксис

class Buffer : storage_t<Buffer<storage_t,void,void>, T2, is_allocated>

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

class Buffer : storage_t<Buffer, T2, is_allocated>

Тогда я бы хотел, чтобы структура mutable_storage распознала специализацию шаблона, такую ​​как

template <typename T2, typename is_allocated>
struct mutable_storage<Buffer, T2, is_allocated> { ... };

(Конечно, это было бы недопустимо, поскольку "Buffer" не является типом, поэтому его также следует изменить).Но то, как это используется сейчас, возможность специализироваться с типом Buffer выглядит немного неприятно.Использование typedef, например,

 typedef Buffer<storage_t, void, void> Buffer_Policy

также кажется немного неприятным.Я ищу более чистый путь.Я пытался создать параметр шаблона шаблона шаблона, но это приводит к бесконечному потоку дополнительных шаблонов внутри параметра шаблона (я не знаю точно, как работает шаблон <...>, так что, может быть, так?), Так какБуфер наследует от чего-то, что требует другого Буфера для объявления storage_t.Я также пытался использовать неявный класс, а именно inner_storage_t.Это также не привело к успеху.У кого-нибудь есть предложения, чтобы сделать программу чище?Кстати, если вы видите какие-либо другие ошибки или недостатки, не стесняйтесь упомянуть об этом.Спасибо за чтение и, возможно, вашу помощь.

1 Ответ

0 голосов
/ 01 июня 2018

Поскольку T1 предназначен только для выбора специализации шаблона, вам на самом деле не нужно использовать Buffer.Вместо этого вы можете использовать тип тега.

Сжатие его в пространстве имен также позволяет избежать загрязнения остальной части пространства имен тегами.

#include <type_traits>

template <typename T1, typename T2, typename is_allocated>
struct mutable_storage {};

namespace storage_tags {
  struct Buffer_T {};
}

template <
    template<typename, typename, typename> class storage_t,
    typename T2           = void,
    typename is_allocated = std::false_type
>
class Buffer : public storage_t<storage_tags::Buffer_T, T2, is_allocated> { 

};
...