在C ++中将字符串打印到临时流对象(Printing a string to a temporary stream object in C++)

编程入门 行业动态 更新时间:2024-10-26 20:34:36
在C ++中将字符串打印到临时流对象(Printing a string to a temporary stream object in C++)

我有一个特殊类型的ostringstream,我试图输出文本作为临时对象,但我遇到了一些麻烦。 要清楚,这基本上就是我想做的事情:

ostringstream() << "PARTY DOWN!" << endl;

现在在你说:“但Zack,那个代码完全没用!在线的最后,对象被破坏了,你怎么知道它是否做了什么?”,听我说。 我不会尝试使用普通的ostringstreams,而是尝试使用析构函数实际提供数据退出对象的路径的派生类。 所以在现实中,它看起来更像这样:

specialstringstream() << "PARTY DOWN!" << endl;

specialstringstream有一个析构函数,它将文本转储到别处。

关于我为什么这样做,我不会详细说明。 你必须相信我对我需要做的事情有意义,并且它非常适合现有的巨大代码库。

这是问题所在:当我这样做时,所有内容都会编译并运行,但是我得到一个指针地址打印到我的输出而不是“PARTY DOWN!” 串。 我确定发生这种情况是因为编译器选择执行流输出的ostream& operator<< (const void* val)是ostream& operator<< (const void* val) ,而不是ostream& operator<< (ostream& out, const char* s ) 。

我对于为什么有一个模糊的想法,但我不知道如何解决它。 如何将char * s打印到字符串流的临时实例中?

这是一个展示行为的SpecialStringStream对象的简短版本:

class SpecialStringStream : public ostringstream { public: SpecialStringStream(ostream* regularStream) { regularStream_ = regularStream; } ~SpecialStringStream() { if (regularStream_ != NULL) (*regularStream_) << str(); } private: ostream* regularStream_; };

当我做类似的事情: SpecialStringStream(someStreamPtr) << "PARTY DOWN!" << endl; SpecialStringStream(someStreamPtr) << "PARTY DOWN!" << endl; ,我在输出中得到一个像“00444D60”的指针地址而不是消息。

编辑:由于我是一个太新的用户回答我自己的问题,这是我已经解决的所有回应。

我提出了以下解决方案,它在Visual C ++ 8和我需要的所有其他编译器下工作。 我创建了一个模板运算符,它基本上剥离了const的Const的SpecialStringStream,将其转换为ostream,并让ostream运算符执行它们的操作。 请在评论中随意将其撕成碎片并警告我所引入的所有可怕的潜在错误!

template <class T> std::ostream& operator<<(const SpecialStringStream &o, T msg) { return static_cast<std::ostream&>(const_cast<SpecialStringStream&>(o)) << msg; }

I have a special type of ostringstream that I am trying to output text to as a temporary object but I'm having some trouble. To be clear, this is essentially what I want to do:

ostringstream() << "PARTY DOWN!" << endl;

Now before you say: "But Zack, that code is totally worthless! The object is destroyed at the end of the line, how would you even know if it did anything?", hear me out. I don't try to do this with plain ostringstreams, but rather a derived class in which the destructor actually provides a path for the data to exit the object. So in reality, it looks a lot more like this:

specialstringstream() << "PARTY DOWN!" << endl;

Where specialstringstream has a destructor which dumps the text elsewhere.

I won't go into too much detail as to why I do this. You'll have to trust me that it makes sense for what I need to do and it fits nicely into an existing, gigantic codebase.

Here's the problem: when I do this, everything compiles and runs, but I get a pointer address printed to my output instead of the "PARTY DOWN!" string. I determined that this is happening because the operator chosen by the compiler to perform the stream output is ostream& operator<< (const void* val), not ostream& operator<< (ostream& out, const char* s ).

I have a vague idea of why but I'm at a loss as to how to work around it. What can I do to get char*s to print into a temporary instance of a stringstream?

Here's a short version of the SpecialStringStream object that exhibits the behavior:

class SpecialStringStream : public ostringstream { public: SpecialStringStream(ostream* regularStream) { regularStream_ = regularStream; } ~SpecialStringStream() { if (regularStream_ != NULL) (*regularStream_) << str(); } private: ostream* regularStream_; };

When I do something like: SpecialStringStream(someStreamPtr) << "PARTY DOWN!" << endl;, I get a pointer address like "00444D60" in my output instead of the message.

EDIT: Since I am too new of a user to answer my own question, here is what I've settled on thanks to all the responses.

I came up with the following solution, which works under Visual C++ 8 and all of the other compilers I needed it to. I created a template operator which basically strips a const SpecialStringStream of its constness, casts it as an ostream, and lets the ostream operators do their thing. Feel free to tear it to shreds in the comments and warn me of all the horrible potential bugs I've introduced!

template <class T> std::ostream& operator<<(const SpecialStringStream &o, T msg) { return static_cast<std::ostream&>(const_cast<SpecialStringStream&>(o)) << msg; }

最满意答案

重载ostream& operator<< (ostream& out, const char*)不可行,因为你的临时不会绑定到非const引用ostream& 。 除了声明局部变量并使用它之外,你可以做的事情并不多(因为你不能将右值转换为左值):

{ specialstringstream ss; ss << "Hello world" << std::endl; // OK, can bind to lvalue }

可能的解决方案:您可以声明另一个接受rvalue引用的重载:

std::ostream & operator<<(specialstringstream && o, const char * s) { return o << s; // note: *not* "std::move(o)" }

The overload ostream& operator<< (ostream& out, const char*) is not viable because your temporary won't bind to the non-const reference ostream&. There isn't really much you can do about that (since you can't cast an rvalue to an lvalue) other than declaring a local variable and using that:

{ specialstringstream ss; ss << "Hello world" << std::endl; // OK, can bind to lvalue }

Possible solution: You could declare another overload that accepts an rvalue reference:

std::ostream & operator<<(specialstringstream && o, const char * s) { return o << s; // note: *not* "std::move(o)" }

更多推荐

本文发布于:2023-08-05 14:09:00,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1434748.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:字符串   中将   对象   Printing   object

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!