Shell
從命名管道獲取標準輸入
我想要做的是在終端視窗中執行 python 並從命名管道重定向它的標準輸入。然後我在另一個終端中寫入命名管道,並在 python 上執行該命令。
1號航站樓:
mkfifo p1 python < p1
2號航站樓:
echo -n "print \"Hello World\"" > p1
會發生什麼 - python 列印
Hello World
並退出。我想要做的是讓 python 執行以執行下一個命令。我如何在外殼中執行此操作?
你需要
- 即使它的標準輸入不是終端,也以互動方式執行 python:使用
python -i
- 保持管道的寫入端打開,否則python將檢測到EOF並退出。
所以:
python -i < p1
在其他地方:
# open p1 on fd 3 of the shell process¹ for instance so stdout is # left untouched in case you still want to write messages there. exec 3> p1 # write something on fd 3. For instance with ksh/zsh's print # builtin: print -u3 '1j*1j' # or for commands such as echo that can only print things # on stdout (fd 1), duplicate that fd 3 to their fd 1: echo '1j*1j' >&3 # short for 1>&3 # after echo (a builtin² in virtually all shells) returns, fd 1 # is restored to what it was before, but fd 3 remains open on # the writing end of the pipe, so python still doesn't see EOF # there. echo normal message on stdout echo 1+1 >&3 # more instructions for python ... # and when done, close that file descriptor so python sees the EOF # (assuming that fd 3 was the only file descriptor left open on # the writing end of that pipe): exec 3>&-
特別是在腳本中,作為替代方案,您可以重定向整個命令組,而不是使用
exec
³ 手動打開和關閉 fd。{ echo ... >&3 ... ... } 3> p1
¹ fd 3 將由子程序繼承,並且(在 ksh93 中設置 close-on-exec 標誌除外)在這些程序中執行的其他命令(如果有)。
² 當然也適用於非內置命令。對於非內置函式,shell 不需要保存和恢復 fd 1,因為重定向只在被派生來執行命令的子程序中執行。對於外部命令,除了在自動執行此操作的 ksh93 中,您實際上可能想要關閉該 fd 3,以便它不會洩露給它們以及它們最終可能產生的後台程序(
cmd >&3 3>&-
)。³ 請注意,在這種情況下,ksh93 不會在該 fd 3 上設置 close-on-exec 標誌。