Я написал следующий класс для извлечения параметров шаблона класса Base
и добавления к нему параметров шаблона класса Derived
во время компиляции:
template <typename...> struct derived_type_traits;
// specialization for the case when Base is not a template
template <typename Base> struct derived_type_traits<Base> {
template <template<typename...> class Derived, typename... DerivedArgs>
using type = Derived<DerivedArgs...>;
};
// specialization for the case when Base is a template
template <template <typename...> class Base, typename... BaseArgs> struct derived_type_traits<Base<BaseArgs...>> {
template <template<typename...> class Derived, typename... DerivedArgs>
using type = Derived<DerivedArgs..., BaseArgs...>;
};
Я использую его как частьзаводских строительных блоков.С помощью этого класса признаков я могу построить Derived
из набора параметров шаблона и класса Base
:
namespace A {
class Base {};
template <typename T>
class Derived : public Base {};
auto ptr = new typename derived_type_traits<Base>::type<Derived, int>();
}
namespace B {
class Base {};
template <typename T1, typename T2, typename T3>
class Derived : public Base {};
auto ptr = new typename derived_type_traits<Base>::type<Derived, int, double, std::string>();
}
namespace C {
template <typename T>
class Base {};
template <typename T1, typename T2, typename T3, typename T>
class Derived : public Base<T> {};
auto ptr = new typename derived_type_traits<Base<int>>::type<Derived, int, double, std::string>();
}
Однако он не работает в следующих случаях:
namespace D {
template <typename T>
class Base {};
template <typename T1, typename T2, template <typename,typename> class T3, typename T>
class Derived : public Base<T> {};
template <typename T1, typename T2> struct Foo {};
auto ptr = new typename derived_type_traits<Base<int>>::type<Derived, int, double, Foo>();
}
namespace E {
template <typename U1, template <typename,typename> class U2>
class Base {};
template <typename T1, typename T2, typename T3, typename U1, template<typename,typename> class U2>
class Derived : public Base<U1,U2> {};
template <typename T1, typename T2> struct Foo {};
auto ptr = new typename derived_type_traits<Base<int, Foo>>::type<Derived, int, double, std::string>();
}
Код теста здесь .
Я знаю, что это связано с тем фактом, что шаблон с переменными параметрами не может соответствовать сочетанию типов и типов шаблонов.
Есть решение или я ошибаюсь?Я могу использовать до C ++ 14 (без C ++ 17).