使用零模板参数的模板可以做什么?

时间:2015-09-12 14:53:32

标签: c++ templates c++11

我前段时间了解到你可以创建零参数的模板。虽然无法直接创建它们,但您可以使用成员模板

template<typename ...T> 
struct Maker {
   template<T...>
   struct HasNParams { };
};

Maker<>::HasNParams<> hnp;

我想知道这是否意图形成良好以及你可以用这些野兽做些什么。你能否将它们作为模板参数传递,并创建明确的特化(我想唯一的情况是空案例)?

2 个答案:

答案 0 :(得分:4)

冒着听起来很明显的风险,结束递归实例化。

template<typename Arg, typename ...T> 
struct Maker : public Maker<T...>
{
   template<T...>
   struct HasNmin1Params { };
};

这里的要点是Maker的实际参数列表不是空的,但我们只在HasNminOneParams中使用N-1个参数。

答案 1 :(得分:1)

考虑以下课程模板:

template <typename... > struct typelist { };

这是容器的元编程等价物。以与空vectormap一样有用的方式,有一个空的typelist很有用。也就是说,typelist<>类型的东西。以下是此类构造的两个示例用例。

它可能是类型递归的终止条件:

void foo(typelist<> ) { }

template <typename T, typename... Ts>
void foo(typelist<T, Ts...> ) {
    bar<T>();
    foo(typelist<Ts...>{});
}

它可能是元函数的“返回”值,表示失败条件。

template <typename F, typename T>
struct filter_one
: std::conditional_t<F::template apply<T>::value,
                     typelist<T>, 
                     typelist<>>
{ };

我们可以用它来编写一个类型列表过滤器元函数:

template <typename F, typename TL>
struct filter;

template <typename F, typename... Ts>
struct filter<F, typelist<Ts...>>
: concat_t<filter_one<F, Ts>...>
{ };

这两个都是typelist<>的非常有用的功能,而这只是一个类模板。