我正在制作一个简单的日志记录类,它带有指向 std::ofstream
或 std::cerr
的指针。
有没有任何简单的方法可以使用智能指针进行自动清理,而不管使用哪个流?
代码必须在 clang++、g++ 和 VS2013 上编译。
代码
#include <iostream>
#include <fstream>
#include <string>
class Logger {
private:
std::ostream * output_stream{ nullptr };
bool using_file{ false };
public:
Logger()
{
output_stream = &std::cerr;
using_file = false;
}
Logger(std::string file)
{
output_stream = new std::ofstream(file);
using_file = true;
}
~Logger()
{
if (using_file)
{
delete output_stream;
}
}
template<typename T>
void log(T info)
{
*output_stream << info << std::endl;
}
};
class tmp {
int i{ 4 };
friend std::ostream & operator<<(std::ostream &os, const tmp& p);
};
std::ostream &operator<<(std::ostream &os, const tmp& p)
{
return os << p.i;
}
int main()
{
tmp t;
Logger logger;
logger.log(t);
system("pause");
return 0;
}
尝试
std::unique_ptr
我可以像这样为文件使用 std::unique_ptr
:
std::unique_ptr<std::ostream> p;
p = std::make_unique<std::ofstream>("file.txt");
*p << "hi there" << std::endl;
尝试使用 std::cout
警告我有关已删除的函数(假设这是构造函数。
std::unique_ptr<std::ostream> p2;
p2 = std::make_unique<std::ostream>(std::cout);
*p2 << "hey" << std::endl;
std::shared_ptr
因为 std::unique_ptr
只用于拥有东西,而 std::cout
不应该被拥有,我想我会尝试 std: :shared_ptr
std::shared_ptr<std::ostream> p;
p = std::make_shared<std::ostream>(std::cout);
*p << "hola" << std::endl;
它给了我同样的 deleted constructor 错误。 p = &std::cout
提示类型不匹配,所以它也不起作用。
最佳答案
您可以将 shared_ptr
与删除器一起使用,该删除器在 cerr
的情况下不删除任何内容,而只是正常构造的 shared_ptr
ofstream
class Logger {
private:
std::shared_ptr<std::ostream> output_stream{ nullptr };
public:
Logger() :
output_stream(&std::cerr, [](std::ostream*){})
{ }
Logger(std::string file) :
output_stream(std::make_shared<std::ofstream>(file))
{ }
// default destructor is OK
template<typename T>
void log(T info)
{
*output_stream << info << std::endl;
}
};
关于c++ - 如何使用智能指针进行自动清理?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31750689/