首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >在使用“`exec 1>file`”之后,如何停止STDOUT的重定向以文件和恢复STDOUT的正常操作?

在使用“`exec 1>file`”之后,如何停止STDOUT的重定向以文件和恢复STDOUT的正常操作?
EN

Stack Overflow用户
提问于 2014-08-24 18:20:08
回答 4查看 17.9K关注 0票数 12

我是shell脚本的新手,我使用的是Ubuntu-11.10。在终端中,使用exec 1>file命令后,无论给终端什么命令,其输出都不会显示在终端中。我知道STDOUT被重定向到文件,这些命令的输出被重定向到文件。

我的问题在这里

  1. 一旦我使用了exec 1>file,我怎样才能摆脱它呢?即如何停止STDOUT的重定向到文件并恢复STDOUT的正常运行(即重定向到终端而不是文件)? 我尝试使用exec 1>&-,但是它没有工作,因为它关闭了STDOUT文件描述符。

  1. 请说明一下exec 1>fileexec 1>&-的整个操作。

  1. 如果我们使用exec 0>&- exec 1>&- exec 2>&-关闭标准文件描述符0、1、2,会发生什么?
EN

回答 4

Stack Overflow用户

回答已采纳

发布于 2014-08-24 19:04:34

Q1

在执行初始exec之前,必须为恢复做好准备。

代码语言:javascript
复制
exec 3>&1 1>file

若要稍后恢复原始标准输出,请执行以下操作:

代码语言:javascript
复制
exec 1>&3 3>&-

第一个exec将原始文件描述符1(标准输出)复制到文件描述符3,然后将标准输出重定向到指定文件。第二个exec再次将文件描述符3复制到标准输出,然后关闭文件描述符3。

Q2

这是一个有点开放的结局。它可以在C代码级别或shell命令行级别进行描述。

代码语言:javascript
复制
exec 1>file

只需将shell的标准输出(1)重定向到指定的文件。文件描述符一现在引用指定的文件;任何写入标准输出的输出都将转到该文件。(请注意,交互式shell中的提示被写入标准错误,而不是标准输出。)

代码语言:javascript
复制
exec 1>&-

只需关闭shell的标准输出即可。现在,标准输出没有打开的文件。如果程序运行时没有标准输出,程序可能会不高兴。

Q3

如果您关闭所有三个标准输入、标准输出和标准错误,交互式shell将在关闭标准输入时退出(因为它在读取下一个命令时将得到EOF )。shell脚本将继续运行,但是它运行的程序可能会被破坏,因为它们保证有3个开放的文件通道--标准输入、标准输出和标准错误--当shell运行它们时,如果没有其他I/O重定向,那么它们就得不到承诺的文件通道,而且可能会崩溃(您知道命令的退出状态可能不会为零--成功)。

票数 23
EN

Stack Overflow用户

发布于 2014-08-25 07:42:38

Q1:在将标准输出重定向到文件之后,有一种简单的方法可以将标准输出还原到终端:

代码语言:javascript
复制
exec >/dev/tty

虽然保存原始的stdout文件描述符通常是以后恢复它所必需的,但在这种情况下,您希望stdout/dev/tty,因此不需要做更多的事情。

代码语言:javascript
复制
$ date
Mon Aug 25 10:06:46 CEST 2014
$ exec > /tmp/foo
$ date
$ exec > /dev/tty
$ date
Mon Aug 25 10:07:24 CEST 2014
$ ls -l /tmp/foo
-rw-r--r-- 1 jlliagre jlliagre 30 Aug 25 10:07 /tmp/foo
$ cat /tmp/foo
Mon Aug 25 10:07:05 CEST 2014

Q2exec 1>file是一种略显冗长的执行exec >file的方式,正如前面所述,只要您有权创建/写入它,就可以将stdout重定向到给定的文件。如果文件不存在,则创建该文件;如果存在,则截断该文件。

exec 1>&-正在关闭stdout,这在大多数情况下可能是个坏主意。

Q3:命令应该是

代码语言:javascript
复制
exec 0<&-
exec 1>&-
exec 2>&-

注意stdin的反向重定向。

可以这样简化:

代码语言:javascript
复制
exec <&- >&- 2>&-

此命令关闭所有三个标准文件描述符。这是个非常糟糕的主意。如果您希望脚本与这些通道断开连接,我建议采用这种更健壮的方法:

代码语言:javascript
复制
exec </dev/null >/dev/null 2>&1

在这种情况下,所有输出都将被丢弃,而不是触发错误,而所有输入只会返回任何内容而不是失败。

票数 9
EN

Stack Overflow用户

发布于 2015-08-26 06:46:02

接受的答案对我来说太冗长了。所以,我决定总结一下你原来的答案。

使用Bash版本4.3.39(2)-release

关于Cygwin机上的x86 32位

给予:

  • 史丁是fd #0。
  • Stdout是fd #1。
  • Stderr是fd #2

答(以bash写):

代码语言:javascript
复制
exec 1> ./output.test.txt
echo -e "First Line: Hello World!"
printf "%s\n" "2nd Line: Hello Earth!" "3rd Line: Hello Solar System!"

# This is uneccessary, but
# it stops or closes stdout.
# exec 1>&-

# Send stdout back to stdin
exec 1>&0

# Oops... I need to append some more data.
# So, lets append to the file.
exec 1>> ./output.test.txt
echo -e "# Appended this line and the next line is empty.\n"

# Send stdout back to stdin
exec 1>&0

# Output the contents to stdout
cat ./output.test.txt

有用-关键词:

在Bourne、Bash、tcsh、zsh ( Linux )、BSD、AIX、HP、Busybox、Toybox等等中,还有文档、字符串和进程替代IO重定向。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/25474854

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档