前言
为什么要将输出结果写入文件呢?
我们知道,标准输出的缓存往往有限制,而你编译的程序产生的log可能会很多,若是超出了缓存便可能造成log不完整。此外,log信息覆盖整个屏幕也不便于查看。
所以将输出结果直接写入文件,从文件中可以看到完整的log信息,方便查找问题。
实践
输出结果显示于屏幕及文件
给出测试文件test.py:
import sys
print("输出到标准输出")
print("输出到标准错误输出", file=sys.stderr)
以执行py文件为例:
(base) [root@node105 ~]$ python test.py | tee log.txt
屏幕输出结果:
另一边,也被写入了log.txt文件中:
可以看到,log.txt中并无标准错误输出,只包含标准输出。屏幕输出结果中包含标准错误输出,且先于标准输出被打印。
命令解读:
|
的含义是管道,作用是提供一个管道,将上一个程序的标准输出重定向到下一个程序作为标准输入。
tee命令用于读取标准输入的数据,并将其内容输出成文件。
所以| tee log.txt
的效果便是将前面程序的标准输出写入到log.txt文件中。
若是不想覆盖原文件内容,而是追加新内容,则在tee后加上-a
即可。
输出结果只显示于文件
当然,我们可能不希望在屏幕上输出,只写入文件,加一个>
重定向便可:
(base) [root@node105 ~]$ python test.py | tee >log.txt
标准输出确实被重定向到文件中,不在屏幕上显示,但是标准错误输出依旧显示于屏幕上。
遂推测,若无特殊声明,以上重定向等操作均只针对标准输出,对标准错误输出无效。
拓展:如果需要合并多个txt文件,只需要如下命令:
(base) [root@node105 ~]$ cat 2007_train.txt 2007_val.txt 2012_*.txt > train.txt
2>&1
由上面的知识延伸到了这一命令,若是想对标准错误输出进行操作,可能要使用这条命令。
在Linux系统中0 1 2是文件描述符,0代表标准输入stdin,1代表标准输出stdout,2代表标准错误输出stderr。
含义:将标准错误输出重定向到标准输出
2为标准错误输出,1为标准输出,>为重定向,&可以理解为引用,&1代表引用此时的标准输出。若是没有&,会被重定向到名为“1”的文件中。
我们知道,前面的命令是不会把标准错误输出写入文件的。
所以,若是打算将标准错误输出也写入文件则可以:
(base) [root@node105 ~]$ python test.py 2>&1 | tee >log.txt
此时,屏幕不再有输出,两种输出全被写入文件。
此处需要注意的是,2>&1的位置是有讲究的。1代表此时的标准输出,执行到2>&1时,1为屏幕,则2也重定向到屏幕,再一起被重定向到log.txt。
在其他案例中,更换2>&1的位置可能会得到不同的结果,具体案例可参照如下链接。
深入理解Linux shell中2>&1的含义(全网最全,看完就懂)