在我的项目中,我使用了一个名为 Message 的类,它继承自 std::ostringstream 来打印出其他类类型的人类可读信息。
所以它的 << 运算符被重载了几次,采用了我想要打印出来的我自己的类类型。
class Message : public ostringstream
{
public:
Message() {};
virtual ~Message() {};
Message& operator <<(const MyTypeA &a) { return *this << a.getStr(); };
Message& operator <<(const MyTypeB &b) { return *this << b.identifier(); };
Message& operator <<(const MyTypeC &c) { return *this << c.foo(); };
// Pass everything unknown down to ostringstream, and always return a Message&
template<class T>
Message& operator <<(const T &t)
{
(std::ostringstream&)(*this) << t;
return *this;
}
};
没有模板
MyTypeA a,b;
Message m;
m << a << "-" << b;
代码无法编译,因为 (m << a << "-") 将返回一个 ostringstream&,它不能接受 'b'。所以我使用模板来确保始终返回 Message&。
我的问题:
Message m;
m << "Hello, world" << std::endl;
生成一个非常长的编译器错误,我不知道为什么。
最佳答案
不要从任何流类派生来创建新流!从std::ostream
派生的唯一原因或 std::istream
是创建一个正确设置的流以使用合适的流缓冲区。您应该从 std::streambuf
派生而不是从流派生创建新的源或目标。要为新类型创建输出运算符,您需要重载 operator<<()
与 std::ostream&
作为第一个参数,您的自定义类型作为第二个参数。同样与 std::istream&
.
顺便说一句,你遇到的问题是因为std::endl
是一个函数模板。试图在某处传递函数模板需要可以推导出适当的实例化。由于您的输出运算符没有包含合适的签名,因此 std::endl
的实例化无法推断。我可以说明需要什么,但这毫无意义,因为无论如何这是错误的方法。
关于c++ - 继承自 std::ostringstream,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23726848/