这个问题来自https://mywiki.wooledge.org/ProcessSubstitution
mkfifo /var/tmp/fifo1
mkfifo /var/tmp/fifo2
sort list1 >/var/tmp/fifo1 &
sort list2 >/var/tmp/fifo2 &
diff /var/tmp/fifo1 /var/tmp/fifo2
rm /var/tmp/fifo1 /var/tmp/fifo2
据我了解命名管道,我认为以下内容有效:
在第 1-2 行中,我们创建了两个命名管道:fifo1 和 fifo2。
sort list1 > fifo1 &
并sort list2 > fifo2 &
尝试写入命名管道,因此它们会被阻塞,直到从其中读取数据为止。
然后diff
接下来的命令从 fifo1 和 fifo2 读取。所以3-4号线畅通无阻。接下来diff
执行并将输出发送到终端。
最后,我们删除命名管道 fifo1 和 fifo2。
消息人士称,这一切都与diff <(sort list1) <(sort list2)
.
我的解释正确吗?
谢谢!
答案1
我的解释正确吗?
不会。sort
s 甚至在启动之前就被阻止了(sort
当尝试执行 s 时,执行 s 的子 shell 会被阻止)打开先进先出)。它们只会被阻塞,直到 fifo 的另一侧被阻塞打开也没有必要读从中得到任何东西。
如果您尝试mkfifo /tmp/fifo; true > /tmp/fifo
,true
即使它从未尝试向 fifo 写入任何内容,也会被阻止。来自另一个 shell 的Atrue < /tmp/fifo
将解锁它,而不尝试读任何事情。
消息人士称,这一切都与
diff <(sort list1) <(sort list2)
.
它不是。如果由于某种原因diff fifo1 fifo2
在打开作为参数传递的 fifo 之前终止,它们sort ... &
将永远留在那里,直到有人怜悯并手动杀死它们。
我不知道进程替换是否真的可以用命名管道来实现,但 FWIW bash 并没有轻易实现这一点;在没有 s 的平台上/dev/fd
,bash 的进程替换是有缺陷的,并且只能非常小心地使用。