如何为类提供几个可变参数模板模板参数

时间:2014-10-23 12:03:12

标签: c++ class c++11 variadic-templates

我应该如何向下面的S类提供模板模板参数?

#include "tuple"
template<
    class C1,
    template<class... C3> class C2,
    class... C3,
    template<class... C5> class C4,
    class... C5
> struct S {};
int main() {
    S<
        int,
        std::tuple<int, char>,
        std::tuple<double>
    > s;
    return 0;
}

GCC 4.8.3抱怨:

expected a class template, got 'std::tuple<int, char>'

我应该使用什么而不是元组? S必须在其operator()中知道C3,但我不能给C3,因为boost :: mpl :: for_each需要operator()的特定签名。以前我通过将tuple<int, char>()作为常规参数来推断模板来处理这个问题,但这似乎不可行。在https://stackoverflow.com/a/12782697/1226313回答了类似的问题,但这似乎只适用于函数而不是类。为了清楚起见,在S的operator()内部,我想将C3(以及C5,C7等)作为参数传递给可变函数。

2 个答案:

答案 0 :(得分:2)

您需要提供模板,而不是类型:

S<int, std::tuple, /* std::tuple */> s;

答案 1 :(得分:0)

模板参数与模板参数不匹配。如果这是主要模板:

template<
    class C1,
    template<class...> class C2,  // note 1
    class... C3,
    template<class...> class C4,  // note 1
    class... C5
> struct S {};

// note 1:我删除了模板模板参数参数包C3C5的名称,因为它们没有用处。

然后你会像这样实例化模板:

S<
    int,
    std::tuple,
    int, char,
    std::tuple,
    double
>

但上述工作不会起作用,因为任何参数包必须位于主模板声明中参数列表的末尾。

如果您希望能够像这样实例化模板:

S<
    int,
    std::tuple<int, char>,
    std::tuple<double>
>

然后您需要意识到std::tuple<int,char>std::tuple<double>不是模板。它们是从模板生成的类。以下主模板将匹配这些参数:

template<
    class C1,
    class C2,
    class C3
> struct S;

如果你想了解元组内部的类型,有很多方法可以做到这一点。以下方式可能不是最好的,但它最接近您最初要求的方式。您可以在主模板后添加部分特化,以便在C2C3成为std::tuple的特化时使用

// Partial specialisation
template<
    class C1,
    class... C3,
    class... C5
> struct S<
    C1,
    std::tuple<C3...>,
    std::tuple<C5...>
> {
    auto operator()() const {
        // do something with C1,C3...,C5... here
    }
};