23. 进程替换

管道 将一个命令的 标准输出 输送到另一个命令的 标准输入 是个强大的技术。但是如果你需要用管道输送_多个_命令的 标准输出 怎么办?这时候 进程替换 就派上用场了。

进程替换 把一个(或多个)进程 的输出送到另一个进程的 标准输入

样板 命令列表要用括号括起来

>(command_list)
<(command_list)

进程替换使用 /dev/fd/<n> 文件发送括号内进程的结果到另一个进程。[1]

"<"或">"与括号之间没有空格,加上空格或报错。

bash$ echo >(true)
/dev/fd/63

bash$ echo <(true)
/dev/fd/63

bash$ echo >(true) <(true)
/dev/fd/63 /dev/fd/62

bash$ wc <(cat /usr/share/dict/linux.words)
 483523  483523 4992010 /dev/fd/63

bash$ grep script /usr/share/dict/linux.words | wc
    262     262    3601

bash$ wc <(grep script /usr/share/dict/linux.words)
    262     262    3601 /dev/fd/63

Bash用两个文件描述符创建管道,--fIn 和 fOut--true标准输入连接 fOut(dup2(fOut, 0)),然后Bash 传递一个 /dev/fd/fIn 参数给 echo 。在不使用 /dev/fd/<n> 的系统里,Bash可以用临时文件(感谢 S.C. 指出这点)。

进程替换可以比较两个不同命令的输出,或者同一个命令使用不同选项的输出。

进程替换可以比较两个目录的内容——来检查哪些文件在这个目录而不在那个目录。

进程替换的一些其他用法:

在子shell中 echo 命令用管道输送给 while-read 循环时会出现问题,下面是避免的方法:

例23-1 不用 fork 的代码块重定向。

下面是个类似的例子。

例 23-2. 重定向进程替换的输出到一个循环内

一个读者发来一个有趣的进程替换例子,如下:

注解 [1] 这个与命名管道(使用临时文件)的效果相同,而且事实上,进程替换也曾经用过命名管道。

最后更新于

这有帮助吗?