我需要在文件上输出命令的输出。假设我的命令是zip -r zip.zip directory
,我需要将(这些选项中的任何一个都可以)附加到文件(假设out.txt
)。到目前为止,我得到了zip zip.zip directory | tee -a out.txt
,但它似乎不起作用,它只是在命令结束时写入整个输出......我怎样才能做到这一点?
谢谢;)
背景(即。为什么?
重定向是即时的 - 当您运行somecommand | tee -a out.txt
时,somecommand
设置将其 stdout直接发送到tee
命令,该命令由其文档定义为未缓冲,从而尽快将其输入上的任何可用内容写入其指定的输出接收器。同样,somecommand >out.txt
设置somecommand
在out.txt
开始之前
就写入它。不是立即刷新缓冲输出。
也就是说:标准的C库和大多数其他工具/语言在stdout上缓冲输出,将小写组合成大写。这通常是可取的,因为减少了对内核空间的调用次数("上下文切换"),有利于执行较少数量的更高效、更大的写入。
因此,您的程序并没有真正等到它退出来写入其输出 - 而是等到它的缓冲区(可能是32kb,或64kb或其他)已满。如果它从未产生那么多输出,那么它只会在关闭输出流时被刷新。
解决方法(如何?-- GNU 版本)
如果你在 GNU 平台上,并且你的程序保持它找到它们的方式保留其文件描述符,而不是尝试显式配置缓冲,你可以使用stdbuf
命令来配置缓冲,如下所示:
stdbuf -oL somecommand | tee -a out.txt
定义标准输出(-o
)在运行somecommand
时为行缓冲(L
)。
解决方法(如何? -- 预期版本)
或者,如果已安装expect
,则可以使用它包含的unbuffer
帮助程序:
unbuffer somecommand | tee -a out.txt
。它实际上将模拟 TTY(就像expect
一样),获得与somecommand
直接连接到控制台时相同的非缓冲行为。
您是否尝试使用此日志command > out.log 2>&1
选项来存档所有内容而不显示任何内容,所有内容都将直接进入文件