【发布时间】:2019-12-21 14:26:13
【问题描述】:
这是基本的代码结构(如果它与问题相关,我会透露更多):
class Outer {
// Forward declaration for the next forward declaration
template <class C> class Inner;
// Forward declaration for the actual Inner class definition
template <class C>
friend std::ostream& operator<<(std::ostream &os, const Inner<C> &obj);
template <class C>
class Inner {
friend std::ostream& operator<< <>(std::ostream &os, const Inner &obj);
};
};
由于内部类是模板化的,我意识到我的operator<< 覆盖也必须如此。另外,第二个friend 声明是一个模板实例化,所以operator<< <C> 只是Outer::Inner<C> 的朋友。
当我在单独的实现文件中定义运算符覆盖时,它看起来像这样:
template <class C>
std::ostream& operator<<(std::ostream &os, const Outer::Inner<C> &obj) {
// definition
}
在过去的几天里,我反复将我的代码重构到一个荒谬的程度,希望能成功。最近,我尝试只在 g++ 上编译 *.h 并收到三个错误消息都针对同一行(带有模板实例化的行)。
outer.h:x:y1: error: declaration of ‘operator<<’ as non-function
friend std::ostream& operator<< <>(std::ostream &os, const Inner &obj);
^~
outer.h:x:y1: error: expected ‘;’ at end of member declaration
outer.h:x:y2: error: expected unqualified-id before ‘<’ token
friend std::ostream& operator<< <>(std::ostream &os, const Inner &obj);
^
尽管广泛搜索了错误输出中给出的短语,但是,我仍然无法解决这个问题,所以如果有 C++ 经验的人知道他们在做什么,我将不胜感激帮助。
【问题讨论】:
-
在定义中删除
<C>- 这不是有效的语法。此外,模板必须在头文件中定义;编译器需要在使用模板时查看定义。 -
哦,有趣。我记得在编写内部类的定义时,我必须将
template <class C> Outer::Inner<C>::Inner() {/*...*/}用于构造函数,而将类似的行用于成员函数,所以我一定很困惑(我应该也删除template <class C>吗?)。此外,我刚刚编译头文件时看到的问题仍然存在。
标签: c++ templates inner-classes friend