我正在使用一种仅在bash中运行的科学软件(称为vasp),并使用Python创建一个可以为我进行多次运行的脚本。当我使用subprocess.check_call正常调用函数时,它工作正常,但当我添加'| tee tee_output'它不起作用。
subprocess.check_call('vasp') #this works
subprocess.check_call('vasp | tee tee_output') #this doesn't
我完全不喜欢python和编程。
答案 0 :(得分:4)
试试这个。它通过shell执行命令(作为字符串传递),而不是直接执行命令。 (它相当于使用-c
标志调用shell本身,即Popen(['/bin/sh', '-c', args[0], args[1], ...])
):
subprocess.check_call('vasp | tee tee_output', shell=True)
但请注意docs中有关此方法的警告。
答案 1 :(得分:2)
你可以这样做:
vasp = subprocess.Popen('vasp', stdout=subprocess.PIPE)
subprocess.check_call(('tee', 'tee_output'), stdin=vasp.stdout)
这通常比使用shell=True
更安全,特别是如果你不相信输入。
请注意,check_call
会检查tee
的返回代码,而不是vasp
,以查看它是否应该引发CalledProcessError
。 (shell=True
方法将执行相同操作,因为这与shell管道的行为相匹配。)如果需要,可以通过调用vasp
来自行检查vasp.poll()
的返回码。 (另一种方法不允许你这样做。)
答案 2 :(得分:2)
不要使用shell = True,它有很多安全漏洞。而是做这样的事情
cmd1 = ['vasp']
cmd2 = ['tee', 'tee_output']
runcmd = subprocess.Popen(cmd1, stdout=subprocess.PIPE)
runcmd2 = subprocess.Popen(cmd2, stdin=runcmd.stdout, stdout=subprocess.PIPE)
runcmd2.communicate()
我知道它更长,但它更安全。
答案 3 :(得分:0)
您可以在文档中找到更多信息: http://docs.python.org/library/pipes.html
只需向t
对象