C++ 模板类和插入提取重载
如何使insertion()运算符在模板类中重载,而不使其内联。我希望将>操作符作为朋友类。 我知道如何使它内联 矩阵类中的内联示例C++ 模板类和插入提取重载,c++,templates,operator-overloading,inline,insertion,C++,Templates,Operator Overloading,Inline,Insertion,如何使insertion()运算符在模板类中重载,而不使其内联。我希望将>操作符作为朋友类。 我知道如何使它内联 矩阵类中的内联示例 friend ostream& operator<<(ostream& ostr, const Matrix<T>& inputMatrix) { ... // create the ostr return ostr; } friend-ostream&operator将代码放在类定义之外的头中。
friend ostream& operator<<(ostream& ostr, const Matrix<T>& inputMatrix)
{
...
// create the ostr
return ostr;
}
friend-ostream&operator将代码放在类定义之外的头中。或者,将其放在.tcc
文件中,并将其包含在标题底部。尝试以下操作:
template <typename T> class Matrix;
template <typename T> std::ostream& operator<<(std::ostream& ostr, const Matrix<T>& m);
template <Typename T>
class Matrix
{
public:
friend ostream& operator<< <T> (ostream& ostr, const Matrix<K>& inputMatrix);
};
// This must be in the same translation unit as the class definition!
template<typename T>
ostream& operator<<(ostream& ostr, const Matrix<T>& inputMatrix)
{
// ...
return ostr;
}
模板类矩阵;
template std::ostream&operator如果您确实希望在外部定义运算符,并且只与类型与此模板实例化一致的运算符实例化交朋友,则正确的语法为:
template <typename T> class test; // forward declare template class
template <typename T> // forward declare the templated operator
std::ostream& operator<<( std::ostream&, test<T> const & );
template <typename T>
class test { // define the template
friend std::ostream& operator<< <T>( std::ostream&, test<T> const & ); // befriend
};
template <typename T> // define the operator
std::ostream& operator<<( std::ostream& o, test<T> const & ) {
return o;
}
模板类测试;//前向声明模板类
模板//正向声明模板化运算符
std::ostream&operator您应该阅读。顺便说一句,作为模板函数,它将隐式内联。下次,请使用编辑窗格顶部的101010
按钮格式化消息中的代码。编辑窗格右侧的“如何编辑”浮动窗口对此进行了解释。我认为您需要在函数定义中使用const Matrix&
。(声明可以使用注入的类名Matrix
来表示Matrix
,但这在定义中不可见。)@aschepler,应该纠正这个问题。第二件事你也是对的——在课堂上,我可以说Matrix
,而不是Matrix
。奇怪的是在操作符的类声明中必须使用不同的标识符,而不是T
。也许这是我使用的GCC版本的一个怪癖,或者可能是一个VisualStudio扩展,允许您这样做。有人知道标准是怎么说的吗?您的版本授予所有操作符友谊。re:the standard:14.5.3p1:“类或类模板的朋友可以是函数模板或类模板,函数模板或类模板的特殊化,或普通(非模板)函数或类。”带有另一个类K
参数的版本将整个函数模板声明为好友。我的pastebin链接中的版本将函数模板的一个特殊化声明为friend。我本来打算在这里写一条评论,但觉得太长了。我的回答中提供了将模板的单个实例化声明为友元的正确代码。您能举例说明为什么必须预先声明模板运算符吗?@Silverrocker:主要原因是该语言的设计考虑了单遍编译器(*)。问题是friend
语句告诉编译器:授予对模板的这个特定实例化的访问权。为了使编译器有意义,模板必须已经声明。它类似于:voidfoo(){bar(5);}模板voidbar(T){}
。在声明泛型模板和专门化之前,不能使用或引用类模板的专门化或实例化。(*)这是一个目标,而不是现实,因为其他原因,所有编译器都需要多次检查输入文件。我在某个地方读到,对初始代码执行较少传递的代码有3次传递——包括预处理器。我无法提供该语句源代码的链接,也不记得它是什么编译器。