2

我对一个简单的可变参数模板函数感到沮丧

constexpr size_t num_args () {
    return 0;
}

template <typename H, typename... T>
constexpr size_t num_args () {
    return 1 + num_args <T...> ();
}

int main () {
    std :: cout << num_args <int, int, int> ();
}

上面没有编译,详见上面链接的问题和后续,但是下面的函数可以编译

template <typename T, typename... Args> void foo (T, Args...);

template <typename... Args> void foo (int, Args...);

void foo () {}

template <typename... Args>
void foo (int x, Args... args)
{
    std :: cout << "int:" << x;
    foo (args...);
}

template <typename T, typename... Args>
void foo (T x, Args... args)
{
    std :: cout << " T:" << x;
    foo (args...);
}

foo (int (123), float (123)); // Prints "int:123 T:123.0"

两者似乎都使用相同的语言机制,但是为什么第一个不好而第二个很好呢?

4

2 回答 2

4

不同的是,第一个函数

constexpr size_t num_args () {
    return 0;
}

不是模板,所以永远不能这样调用

num_args <T...> ();
于 2011-08-18T16:55:32.673 回答
0

我开始认为不同之处在于

foo (args...);

利用重载而

num_args <T...> ();

利用专业化。

重载可以处理基本情况,但特化不能用于函数模板(但它可以用于类),这就是auxilliary_class<Args...>::value惯用的原因。

于 2011-08-19T08:45:57.223 回答