这个问题可能听起来有点愚蠢,但我确实看不出重定向和管道之间的区别。
重定向用于重定向 stdout/stdin/stderr,例如ls > log.txt
。
管道用于将一个命令的输出作为另一个命令的输入,例如ls | grep file.txt
。
但为什么同一个事物会有两个操作符呢?
为什么不直接写入ls > grep
以传递输出,这不也是一种重定向吗?我遗漏了什么?
答案1
管道用于将输出传递到另一个程序或实用程序。
重定向用于将输出传递到文件或流。
例如:thing1 > thing2
vsthing1 | thing2
thing1 > thing2
- 你的 shell 将运行名为
thing1
- 输出的所有内容
thing1
都将放置在名为的文件中thing2
。(注意 - 如果thing2
存在,它将被覆盖)
如果您想将程序的输出传递thing1
给名为的程序thing2
,您可以执行以下操作:
thing1 > temp_file && thing2 < temp_file
这将
- 运行名为的程序
thing1
- 将输出保存到名为
temp_file
- 运行名为 的程序
thing2
,假装键盘前的人输入了 的内容temp_file
作为输入。
thing1 | thing2
但是,这很笨重,所以他们制作了管道作为更简单的方法。thing1 > temp_file && thing2 < temp_file
编辑以提供评论中问题的更多详细信息:
如果>
尝试同时“传递给程序”和“写入文件”,则可能会在两个方向上引起问题。
第一个例子:您正在尝试写入文件。已经存在一个您希望覆盖的同名文件。但是,该文件是可执行的。据推测,它会尝试执行此文件,并传递输入。您必须执行一些操作,例如将输出写入新文件名,然后重命名该文件。
第二个例子:正如 Florian Diesch 指出的那样,如果系统中其他地方有另一个同名的命令(即在执行路径中),该怎么办?如果您打算在当前文件夹中创建一个同名文件,那么您将陷入困境。
第三:如果您输入了错误的命令,它不会警告您该命令不存在。现在,如果您输入,它ls | gerp log.txt
会告诉您bash: gerp: command not found
。如果>
意味着两者,它只会为您创建一个新文件(然后警告它不知道如何处理log.txt
)。
答案2
摘自《Unix和Linux系统管理手册》:
重定向
shell 将符号 <、> 和 >> 解释为重新路由命令的输入或输出文件。
管道
要连接一个命令到 STDIN其他使用 | 符号,通常称为管道。
所以我的解释是:如果是命令到命令,请使用管道。如果要输出到文件或从文件输出,请使用重定向。
答案3
如果的含义foo > bar
取决于是否有一个名为的命令bar
,那么使用重定向将变得更加困难并且更容易出错:每次我想要重定向到一个文件时,我首先必须检查是否有一个名为像我的目标文件的命令。
答案4
这两个运算符之间存在着重要区别:
ls > log.txt
--> 此命令将输出发送到 log.txt 文件。ls | grep file.txt
--> 此命令通过使用管道 (|
) 将 ls 的输出发送给 grep 命令,grep 命令在前一个命令提供给它的输入中搜索 file.txt。
如果你必须使用第一个场景执行相同的任务,那么它将是:
ls > log.txt; grep 'file.txt' log.txt
因此,管道(带有|
)用于将输出发送到其他命令,而重定向(带有>
)用于将输出重定向到某个文件。