SFINAE 优雅地检查"template template class"(在模板参数中)
SFINAE to check "template template class" (in template argument) elegantly
如何在模板参数中检查模板模板类的类型?
例
B<T>
和C<T>
是模板类。
我想创建一个可以D<B>
或D<C>
的类D<class BC>
。
只有D<B>
有D::f()
.
这是我的解决方法(演示(。它有效。
#include <iostream>
using namespace std;
class Dummy{};
template<class T>class B{};
template<class T>class C{};
template<template<class T> class BC>class D{
//f() is instantiated only if "BC" == "B"
public: template<class BCLocal=BC<Dummy>> static
typename std::enable_if<std::is_same<BCLocal,B<Dummy>>::value,void>::type f(){
}
//^ #1
};
int main() {
D<B>::f();
//D<C>::f(); //compile error as expected, which is good
return 0;
}
#1
行很长而且很丑(使用 Dummy
来破解(。
在实际程序中,它也容易出错,特别是当B<...>
和C<...>
可以有 5-7 个模板参数时。
有没有办法改进它?
我梦想着这样的东西:-
template<class BCLocal=BC> static
typename std::enable_if<std::is_same<BCLocal,B>::value,void>::type f(){
}
为什么不直接将比较提取到一个方便的实用程序中呢?
#include <type_traits>
template<template<class...> class L, template<class...> class R>
struct is_same_temp : std::false_type {};
template<template<class...> class T>
struct is_same_temp<T, T> : std::true_type {};
那么f
上的SFINAE可以简单地看起来像这样:
static auto f() -> typename std::enable_if<is_same_temp<BC, B>::value>::type {
}
无需为enable_if
指定void
,因为它是它提供的默认类型。
我认为,尾随返回类型也具有美化效果。
有了C++14,我们可以进一步美化。首先是变量模板。
template<template<class...> class L, template<class...> class R>
using bool const is_same_temp_v = is_same_temp<L, R>::value;
然后使用std::enable_if_t
模板别名:
static auto f() -> std::enable_if_t<is_same_temp_v<BC, B>> {
}
相关文章:
- 传递给std::function template的template参数究竟代表什么
- 模板函数参数到模板函数的"candidate template ignored: could not match ..."
- 为什么std::{container}::template不能推导其参数类型
- 按参数类型更改"return type template"
- SFINAE 优雅地检查"template template class"(在模板参数中)
- 为什么可变参数模板在模板介绍中不起作用,但在要求子句中起作用?ConceptName{T,U,V,W} <-- template<typename ...T>
- std::pair中的template-template参数
- 重新定义类<template-parameter-1-2>的默认参数
- template元编程:将一堆模板参数相乘
- "Unable to resolve template based identifier X" - 从模板类调用模板参数类的方法 (C++)
- 带有Template参数的Template函数
- Template()的参数转发使构造函数参数变为常量
- 使用template-template参数作为类函数的返回类型
- 更改专用化"template<...>"行中模板参数的顺序是否会导致定义重复或歧义?
- static_assert是否需要使用template参数
- 根据Template参数包装类型的容器的Template类
- 使用template-template参数从可变模板合并类型
- 如何不指定模板内部模板(+template)参数
- 在C++中的Template中定义类的新对象,错误:缺少Template参数
- 为什么std::stack不使用template-template参数