【问题标题】:Using same stream object to write to filestream or stringstream使用相同的流对象写入文件流或字符串流
【发布时间】:2019-09-02 16:59:00
【问题描述】:

我正在尝试使用 ostream 对象写入基于字符串流的用户输入文件流(类似于 Linux 中的 fmemopen)。

我意识到 ostream 不采用 stringstream 或 fstream 对象,而是采用 stringbug 或 filebuf。

我尝试了以下代码:

    char content[] = "This is a test";
    if (isFile)
    {
        filebuf fp;
        fp.open(filename, ios::out);
        ostream os(&fp);
        os << content;
        fp.close();
    }
    else
    {
        stringbuf str;
        ostream os(&str);
        os << content;
    }

这在 if else 条件下工作正常,但我想在 if else 条件之外使用ostream os,作为os &lt;&lt; content。但是问题是我无法全局定义 ostream os,因为 ostream 没有这样的构造函数。

有没有办法解决这个问题?

【问题讨论】:

  • 将数据的写入与输出机制的设置分开。编写一个将数据插入流的函数。该函数应该通过引用获取std::ostream 并将数据写入那里。调用函数时,请根据需要传递std::ofstreamstd::ostringstream
  • 这是我可以使用的。有没有办法默认初始化insertdata(ostream&amp; os)insertdata(ostream&amp; os = ofstream("temp.txt",ios::out)?这给了我一个错误。如果我创建const ostream&amp; os,它会起作用,但是 os.write 会引发编译错误。
  • @Trancey 非常量引用无法绑定到临时对象。此外,这不是使用默认值有意义的场景。调用者需要指定函数应该写入的流类型。

标签: c++ fstream stringbuffer sstream filebuf


【解决方案1】:

这可以通过几种不同的方式来处理。

使用辅助函数:

void write(ostream &os, const char *content)
{
    os << content
}

...

char content[] = "This is a test";
if (isFile)
{
    ofstream ofs(filename);
    write(ofs, content);
}
else
{
    ostringstream oss;
    write(oss, content);
    string s = oss.str();
    // use s as needed...
}

或者,使用 lambda:

char content[] = "This is a test";
auto write = [](ostream &os, const char *content){ os << content; }

if (isFile)
{
    ofstream ofs(filename);
    write(ofs, content);
}
else
{
    ostringstream oss;
    write(oss, content);
    string s = oss.str();
    // use s as needed...
}

改用指针:

char content[] = "This is a test";
std::unique_ptr<ostream> os;

if (isFile)
    os = std::make_unique<ofstream>(filename);
else
    os = std::make_unique<ostringstream>();

*os << content;

if (!isFile)
{
    string s = static_cast<ostringstream*>(os.get())->str(); // or: static_cast<ostringstream&>(*os).str()
    // use s as needed...
}

【讨论】:

  • 这有帮助! *os &lt;&lt; content 对于 ostringstream,可以将其写入 ostringstream 对象吗?似乎我可以从 streambuf 指针 rdbuf 中检索它,但我无法将其放入标准字符串或字符串流中。
  • 我的错误,*oss &lt;&lt; content 应该是 *os &lt;&lt; content。是的,这可以写给ostringstream,因为它是ostream 的后代。之后要获取string,您可以将ostream 转换回ostringstream,这样您就可以调用它的str() 方法。我已经更新了我的答案以表明
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2012-09-08
  • 2018-05-25
  • 2023-03-29
  • 2011-05-03
  • 1970-01-01
  • 2012-03-25
  • 1970-01-01
相关资源
最近更新 更多