为什么subprocess.Popen不工作时,参数序列?

我有一个subprocess.Popen时args参数给出序列的问题。

例如:

import subprocess maildir = "/home/support/Maildir" 

这工作(它打印/ home / support / Maildir目录的正确大小):

 size = subprocess.Popen(["du -s -b " + maildir], shell=True, stdout=subprocess.PIPE).communicate()[0].split()[0] print size 

但是,这不起作用(尝试):

 size = subprocess.Popen(["du", "-s -b", maildir], shell=True, stdout=subprocess.PIPE).communicate()[0].split()[0] print size 

怎么了?

从文档

在Unix上,shell = True:[…]如果args是一个序列,则第一个项目指定命令string,任何附加项目将被视为shell本身的附加参数 。 也就是说,Popen相当于:

 Popen(['/bin/sh', '-c', args[0], args[1], ...]) 

在你的情况下翻译为:

 Popen(['/bin/sh', '-c', 'du', '-s', '-b', maildir]) 

这意味着-s-bmaildir被shell解释为选项,而不是du (在shell命令行中试试!)。

由于shell=True在你的情况下不需要,你可以删除它:

 size = subprocess.Popen(['du', '-s', '-b', maildir], stdout=subprocess.PIPE).communicate()[0].split()[0] 

另外,你可以使用你的信号方法,但在这种情况下你不需要列表。 您还必须注意目录名称中的空格:

 size = subprocess.Popen('du -s -b "%s"' % maildir, shell=True, stdout=subprocess.PIPE).communicate()[0].split()[0] 

从文件来看,

在Unix上, shell = True :如果args是一个string ,它指定了通过shell执行的命令string。 如果args是一个序列 ,则第一个项目指定命令string,任何其他项目将被视为附加的shell参数。

所以,试试吧

 subprocess.Popen("du -s -b " + maildir, ... 

要么

 subprocess.Popen(["du","-s","-b",maildir], ... 

它应该是["du", "-s", "-b", maildir]