【问题标题】:Pipe to my program as a log rotator管道到我的程序作为日志旋转器
【发布时间】:2015-10-31 20:55:20
【问题描述】:

我正在尝试实现我自己的日志轮换器(只要文件大小达到 10 MB,就创建新的日志文件)。读取标准输入并将其写入文件的部分是这样的:

fstream file("log.txt", ios::out | ios::app);
while (std::cin >> lineInput) {
    file << lineInput;
}

但问题是管道数据被破坏了。制表符和新行总是丢失。所以例如如果我的程序名称是LogRotator,那么命令:

ls | ./LogRotator

只需将所有文件名连接在一起,如下所示:

LogRotatormain.oMakefile

而ls 的输出是:

LogRotator main.o Makefile

我的问题:如何让标准流式传输保留所有内容,包括制表符、换行符等?

【问题讨论】:

  • 您可以省略格式化的输入/输出,而改用读/写(和类似的)

标签: c++ linux terminal pipe stdin


【解决方案1】:

感谢 Dieter Lücking 的提示,我找到了方法。所以必须使用未格式化的读取。以下工作正常:

fstream file("log.txt", ios::out | ios::app);
while (getline(cin,lineInput,'\n'))
{
    file << lineInput;
}

【讨论】:

  • 究竟是什么让它“未格式化”?它的格式如此之大,完全无法移植,考虑到您使用的是纯 STL,这真是太棒了。
  • @Blindy 该函数不做任何字符串处理,也不根据输入的内容来判断输入(除非满足分隔符,但分隔符也随文本一起传递)。它在阅读时交付它。流式传输到std::cin 等其他处理将修改输入一些时间。例如,它会将\n 更改为新行。我是这样理解的。
  • 肯定不会,流块复制是用ifstream::read 和ofstream::write 完成的。 getline 和 operator&lt;&lt; 都会更改您的数据,并且这在逐个操作系统的基础上进行了详尽的记录。
  • @Blindy 我不是该主题的专家,但仍在学习中。但是这段代码有效,看起来根本不像修改数据。我的日志很好!这该如何解释?
  • @Blindly:当然getline 如果是格式化的 io 函数并且应该只用于文本,而不是二进制。但它逐行读取文本,不修改行中的文本......除了最终的字符集转换。所以这正是量子物理学家想要的。他不想在一行中间更改日志文件,应该明确处理原始 io 函数
猜你喜欢
  • 2017-06-06
  • 1970-01-01
  • 1970-01-01
  • 2017-04-18
  • 1970-01-01
  • 1970-01-01
  • 2012-08-05
  • 1970-01-01
相关资源
最近更新 更多