是否有可能以某种方式进行模板函数专门化,如下所示:
template<typename T, typename... Args>
void Func(size_t id, Args... args) { std::cout << "1\n" }
template<>
void Func<SomeClass>(size_t id, Args... args) { std::cout << "2\n" }
所以我想保留可变参数,但指定 T = SomeClass:
Func<A>(1, 2, 3); // 1
Func<SomeClass>(1, 2); // 2
我知道我可以使用“小技巧” - 将 func 包装到一个类中并对其进行部分专业化,但在我的情况下,这不起作用,因为 Func() 实际上是一些类方法,并且它初始化了该类的一些成员班级。所以 hack-class 应该有指向它的指针并成为它的朋友(因为成员是私有的),这也是问题。
而且这个 hack 看起来有点可怕且难以理解。
您可以通过将函数包装在模板类(结构)中来做到这一点,如下所示:
#include <iostream>
#include <utility>
struct A;
struct SomeClass;
// wrap the functions in a struct
// this can really be helpful
// for template specializations
template<typename T>
struct Wrapper
{
template<typename... Args>
static void Func(size_t id, Args&&... args) // use rvalue references for args (avoids copying of temporaries)
{
std::cout << "id = " << id << ", args : ";
// use std::forward to keep "rvalue" reference(ness)
((std::cout << std::forward<Args>(args) << " "),...); // C++17 fold expression
std::cout << "\n";
}
};
template<>
struct Wrapper<SomeClass>
{
template<typename... Args>
static void Func(std::size_t id, Args&&... args)
{
std::cout << "SomeClass : ";
std::cout << "id = " << id << ", args : ";
((std::cout << std::forward<Args>(args) << " "),...); // C++17 fold expression
std::cout << "\n";
}
};
int main()
{
Wrapper<A>::Func(1ul, 2, 3); // 1
Wrapper<SomeClass>::Func(1ul, 2); // 2
}