【发布时间】:2018-11-26 10:40:42
【问题描述】:
通常,您可以针对实例化的模板类部分专门化模板类。比如
template<class T>
struct specialize_me {};
template<class T>
struct specialize_me<std::vector<T>> {
static const int foo = 3;
};
模板类specialize_me 部分专门针对实例化的模板类std::vector<T>。当specialize_me 用std::vector<T> 实例化时,会选择此特化,适用于任何类T。
int main() {
std::cout << specialize_me<std::vector<int>>::foo; // Compiles.
}
但是,我不知道如何针对实例化的嵌套模板类专门化模板模板类:
// Nested template class.
template<class T>
struct Either {
template<class U>
struct Or {};
};
template<template<class> class T>
struct specialize_me_2 {};
template<class T>
struct specialize_me_2<Either<T>::template Or> {
static const int foo = 3;
};
在这种情况下,当我为任何类T 使用类Either<T>::template Or 实例化specialize_me_2 时,未选择特化。我的猜测是,发生这种情况是因为编译器必须确认或否认,“存在一个 T 使得 Either<T>::template Or 与 specialize_me_2 实例化的类型相同”才能选择我的专业化,而事实并非如此编程或指定这样做。
int main() {
std::cout << specialize_me_2<Either<int>::Or>::foo; // Does not compile. 'foo' is not a member of specialize_me_2<Either<int>::Or>.
}
有没有办法专门化specialize_me_2,以便在任何T 用Either<T>::Or 实例化specialize_me_2 时选择专门化?
这个Either结构体最终会代表一个携带错误的类型,所以Either<T>表示T是错误类型,Either<T>::Or<U>表示U是成功携带的类型计算。
如果这是不可能的,我可能仍然可以使用#defines 让您根据需要为每个T 定义Either<T>,其中#define 还包括specialize_me_2 专门化特别是Either<T>::Or。事实上,我打算在程序中使用Either 结构,无论如何都要写template<class T> using FooError = Either<Foo>::Or<T>,然后写FooError<Bar>、FooError<Quux> 等等,所以使用它不会与预期的用法有很大的不同。
【问题讨论】:
-
我不明白这个。在您的第二个示例中,
Or应该用什么实例化? -
模板参数类型推导仅适用于
::的右侧,因此编译器无法在Either<T>::template Or中推导T。
标签: c++ templates template-specialization