输出到stdout和带有cout、cerr、clog甚至用户定义的ostream的文件

Outputting to a stdout and a file with cout, cerr, clog, or even user defined ostreams

本文关键字:用户 定义 文件 ostream clog cerr stdout cout 输出      更新时间:2023-10-16

问题

我一直在寻找一种方法来实现将cout、cerr等输出到控制台和文件的方法,不幸的是,我对缓冲区的了解非常缺乏,所以详细解释一下一切都在做什么会很好。

我能做的最令人印象深刻的事情是:

//Includes not shown
std::ofstream file ("out.txt");
std::streambuf* fileSb = file.rdbuf();
cout.rdbuf(fileSb);

但即使我的知识有限,根据我对结构的研究,我也有一些想法:

main.cpp

#include <iostream>
#include <fstream>
#include "dualBuffer.h"
int main () {
    std::ofstream file ("out.txt");
    dualBuffer(cout, file);
    std::cout << "Hellow world!" << std::endl; //This outputs to console and file 
}

dualBuffer.h

#include <iostream> 
class dualBuffer : public streambuf /*Maybe ostream as well ????*/ {
public:
    dualBuffer (std::ostream & os1, std::ostream& os2)
        : *os1b ( os1.rdbuf() )
        , *os1b ( os2.rebuf() )
        { }
    //Another constructor if streambuf* is passed instead
private:
    std::streambuf *os1b, *os2b;
}
//May have typos or bugs

其中一个要求是它都建立在标准库之上,不依赖于外部或操作系统,另一个是我希望它在dualBuffer构造函数完成任务后,cout在程序的每个部分都具有相同的属性

您的需求改变了cout的正常行为,这会使代码变得混乱。为什么不使用另一个类来执行此操作呢。像这样:

#include <fstream>
#include <iostream>
class GeneralOStream
{
public:
    GeneralOStream(std::ostream& stdStream, std::ostream& fileStream)
        :_stdStream(stdStream)
        , _fileStream(fileStream)
    {
    }
    template<typename T>
    friend GeneralOStream& operator << (GeneralOStream& stream, const T& t);
private:
    std::ostream& _stdStream;
    std::ostream& _fileStream;
};
template<typename T>
GeneralOStream& operator << (GeneralOStream& stream, const T& t)
{
    stream._stdStream << t;
    stream._fileStream << t;
    return stream;
}
int main() 
{
    std::ofstream file("out.txt");
    GeneralOStream gos(std::cout, file);
    std::cout << "Hellow world!" << std::endl; //This outputs to console and file 
}