以嵌套 class 作为参数的朋友模板声明
Friend template declaration with nested class as argument
C++ FAQ 提供了如何编写友元模板声明的指南。但是当其中一个参数是模板 class 的嵌套结构时,我遇到了问题,例如:
template<typename T>
class MyClass;
template<typename T> QDataStream &operator<<(QDataStream &stream, const typename MyClass<T>::Node &node);
这些版本都不起作用:
template<typename T>
class MyClass
{
private:
struct Node {};
friend QDataStream &operator<< <>(QDataStream &stream, const Node &node);
friend QDataStream &operator<< <>(QDataStream &stream, const MyClass::Node &node);
friend QDataStream &operator<< <>(QDataStream &stream, const MyClass::Node &node);
friend QDataStream &operator<< <>(QDataStream &stream, const typename MyClass<T>::Node &node);
friend QDataStream &operator<< <>(QDataStream &stream, const typename MyClass::Node &node);
};
template<typename T>
QDataStream &operator<<(QDataStream &stream, const typename MyClass<T>::Node &node)
{
return stream;
}
给出的错误(MSVC 2017)是:
error: C2672: '<<': no matching overloaded function found
写这个的正确语法是什么?
此 operator<<
永远不能用作运算符,因为 T
仅出现在非推导上下文中。出于同样的原因,编译器在试图准确找出您要匹配的函数模板的特化时无法推断出模板参数。
还有一个小问题,就是特化命名了它无权访问的私有成员 Node
(编译器无法弄清楚 friend
声明授予它这样的访问权限,直到它会找出声明中指定的专业。
通常的解决方法是将运算符定义为 class 模板定义中的内联非模板函数,或者将 Node
提取到它自己的 class 模板中。
C++ FAQ 提供了如何编写友元模板声明的指南。但是当其中一个参数是模板 class 的嵌套结构时,我遇到了问题,例如:
template<typename T>
class MyClass;
template<typename T> QDataStream &operator<<(QDataStream &stream, const typename MyClass<T>::Node &node);
这些版本都不起作用:
template<typename T>
class MyClass
{
private:
struct Node {};
friend QDataStream &operator<< <>(QDataStream &stream, const Node &node);
friend QDataStream &operator<< <>(QDataStream &stream, const MyClass::Node &node);
friend QDataStream &operator<< <>(QDataStream &stream, const MyClass::Node &node);
friend QDataStream &operator<< <>(QDataStream &stream, const typename MyClass<T>::Node &node);
friend QDataStream &operator<< <>(QDataStream &stream, const typename MyClass::Node &node);
};
template<typename T>
QDataStream &operator<<(QDataStream &stream, const typename MyClass<T>::Node &node)
{
return stream;
}
给出的错误(MSVC 2017)是:
error: C2672: '<<': no matching overloaded function found
写这个的正确语法是什么?
此 operator<<
永远不能用作运算符,因为 T
仅出现在非推导上下文中。出于同样的原因,编译器在试图准确找出您要匹配的函数模板的特化时无法推断出模板参数。
还有一个小问题,就是特化命名了它无权访问的私有成员 Node
(编译器无法弄清楚 friend
声明授予它这样的访问权限,直到它会找出声明中指定的专业。
通常的解决方法是将运算符定义为 class 模板定义中的内联非模板函数,或者将 Node
提取到它自己的 class 模板中。