subprocess.Popen - 再次重定向stdin

时间:2016-06-13 02:02:31

标签: python python-2.7 subprocess popen

我们假设有一个名为'ABC'的程序,它从stdin中读取4个整数并对它们做一些事情。

最近,我倾向于我们可以使用管道将输入提供给ABC,如下所示:

# send.py
import subprocess

p = subprocess.Popen(['ABC'], stdin = subprocess.PIPE)
print >>p.stdin, '1 2 3 4'

我的问题是:我们可以在调用subprocess.Popen之后再次重定向stdin吗?例如,

# send.py
import subprocess

p = subprocess.Popen(['ABC'], stdin = subprocess.PIPE)
print >>p.stdin, '1 2 3'

(Redirect p.stdin to terminal's stdin)

,这样我们就可以通过在终端输入来输入第四个整数到ABC。

2 个答案:

答案 0 :(得分:1)

重定向发生在执行ABC之前,例如,(在Unix上)fork()之后但execv()之前(look at dup2() calls)。在Popen()返回后使用相同的操作系统级别机制进行重定向为时已晚,但您可以手动模拟它。

要在进程运行时“将p.stdin重定向到终端的stdin”,请致电shutil.copyfileobj(sys.stdin, p.stdin)。可能存在缓冲问题,并且子进程可以在其标准输入之外读取,例如直接从tty读取。见Q: Why not just use a pipe (popen())?

您可能想要pexpect's .interact()(未经测试):

#!/usr/bin/env python
import pexpect  # $ pip install pexpect

child = pexpect.spawnu('ABC')
child.sendline('1 2 3')
child.interact(escape_character=None) # give control of the child to the user

答案 1 :(得分:1)

您可以预先要求第四个整数,然后将其与其他3整数一起发送:

p = subprocess.Popen(['ABC'], stdin=subprocess.PIPE)
fourth_int = raw_input('Enter the 4th integer: ')
all_ints = '1 2 3 ' + fourth_int
p.communicate(input=all_ints)