Mic*_*ael 5 c++ variadic-templates c++11
我有一些可变参数模板方法,如下所示:
template<typename ... Args>
void Invoke(const char* funcName, Args ... args) const;
template<typename ... Args>
void Invoke(const char* funcName, Args ... args) const
{
SPrimitive params[] = { args ... };
SomeOtherInvoke(funcName, params, sizeof ... (Args));
}
Run Code Online (Sandbox Code Playgroud)
这里 SPrimitive - 只是一个简单的结构,带有任何原始类型的构造函数。
我想为一些复杂类型再做一个 Invoke 定义。这是我的问题:是否可以在 c++ 11/14 中使可变参数模板方法专业化?我的意思是这样的(为简单起见,让我的类型为 int):
template<int ... Args>
void Invoke(const char* funcName, Args ... args)
{
int params[] = { args ... };
SomeComplexInvoke(funcName, params, sizeof ... (Args));
}
Run Code Online (Sandbox Code Playgroud)
这里我想要一个特殊化,它接受任何 int 类型的参数计数,所以我可以这样称呼它:
Invoke("method", 2, 4 ,9);
Run Code Online (Sandbox Code Playgroud)
正如@Jarod42 所提到的,它不应该通过专业化来完成。在您的示例中,如果所有参数类型都是int,您需要一些特殊的东西,所以让我们编写一个模板来检查它:
template<typename ref, typename t, typename ...types>
struct all_same {
static constexpr bool value = std::is_same<ref, t>::value && all_same<ref, types...>::value;
};
template<typename ref, typename t>
struct all_same<ref, t> {
static constexpr bool value = std::is_same<ref, t>::value;
};
Run Code Online (Sandbox Code Playgroud)
它检查第一个类型参数是否等于所有其他类型参数。然后Invoke我们应该params根据args...类型选择类型:
template<typename ... Args>
void Invoke(const char* funcName, Args ... args)
{
using params_type = typename std::conditional<all_same<int, Args...>::value, int, SPrimitive>::type;
params_type params[] = { args ... };
SomeOtherInvoke(funcName, params, sizeof ... (Args));
}
Run Code Online (Sandbox Code Playgroud)
现在为了演示起见,让我们定义:
struct SPrimitive{
};
void SomeOtherInvoke(const char*, SPrimitive*, size_t) {
std::cout << "Invoked for SPrimitive\n";
}
void SomeOtherInvoke(const char*, int*, size_t) {
std::cout << "Invoked for int\n";
}
Run Code Online (Sandbox Code Playgroud)
并打电话
Invoke("foo", SPrimitive());
Invoke("foo", SPrimitive(), SPrimitive());
Invoke("foo", 1, 2, 3, 4);
Run Code Online (Sandbox Code Playgroud)
输出是:
template<typename ref, typename t, typename ...types>
struct all_same {
static constexpr bool value = std::is_same<ref, t>::value && all_same<ref, types...>::value;
};
template<typename ref, typename t>
struct all_same<ref, t> {
static constexpr bool value = std::is_same<ref, t>::value;
};
Run Code Online (Sandbox Code Playgroud)
这就是你所要求的。
| 归档时间: |
|
| 查看次数: |
1107 次 |
| 最近记录: |