重定向和管道

💡 原文中文,约2700字,阅读约需7分钟。
📝

内容提要

Linux 中的 init 进程创建了标准输入、输出和错误的文件描述符。程序可以通过重定向将输出和错误信息保存到文件,使用 /dev/null 丢弃输出。输入重定向和 Here Document 允许从文件或多行输入获取数据,管道则可以将一个命令的输出作为下一个命令的输入,并处理错误信息。

🔎

延伸解读

重定向中的文件描述符与特殊设备

Linux 中每个进程默认拥有三个文件描述符:0(stdin)、1(stdout)和2(stderr)。重定向时,stdout 的1可以省略,但stderr的2必须显式写出。特殊设备 /dev/null 和 &- 都表示丢弃输出,但 &- 是关闭描述符,而 /dev/null 是写入空设备。理解这些区别有助于精确控制命令的输出流向。

合并 stdout 和 stderr 的正确方式

将 stdout 和 stderr 重定向到同一文件时,若分别写 > out.log 2> out.log,文件会被打开两次,导致内容相互覆盖。正确做法是 > out.log 2>&1,这样 stderr 被重定向到 stdout,而 stdout 已指向 out.log,文件只打开一次。类似地,管道中可用 2>&1 | 或简写 |& 将 stderr 一并传递给下一个命令。

输出重定向的覆盖与追加行为

使用 > 重定向输出时,如果目标文件已存在,会先删除再创建,无论命令是否执行成功都会创建文件。而使用 >> 时,若文件存在则以追加方式打开,不存在则创建。这一区别在日志记录或需要保留历史输出时尤为重要,避免意外覆盖已有数据。

Here Document 的语法细节

Here Document 通过 << delimiter 将多行内容传递给命令,直到遇到单独一行的 delimiter 为止。结尾的 delimiter 前后不能有任何字符,起始处的 delimiter 前后空白字符会被忽略。常用的 EOF 并非强制,可自定义如 SOMETHING。它适合在脚本中嵌入多行输入,避免临时文件。

❓

Q&A

Linux 中的 init 进程创建了哪些文件描述符?

init 进程创建了标准输入、标准输出和标准错误三个文件描述符。

如何在 Linux 中将命令的输出重定向到文件?

可以使用语法 cmd [1-n]> [文件] 将命令的输出重定向到指定文件。

什么是 Here Document,如何使用它?

Here Document 是一种特殊的重定向方式,可以用来将多行输入传递给命令,使用方式为 cmd << delimiter ... delimiter。

如何将标准错误和标准输出同时重定向到同一个文件?

可以使用语法 cmd > out.log 2>&1 将 stdout 和 stderr 同时重定向到 out.log 文件。

管道在 Linux 中的作用是什么?

管道可以将一个命令的标准输出作为下一个命令的标准输入,但无法处理标准错误。

如何使用 /dev/null 丢弃命令的输出?

可以使用命令 2> /dev/null 或者 > /dev/null 来丢弃标准输出或标准错误。

🏷️

标签

➡️

继续阅读