subprocess.Popen可选参数

时间:2016-04-04 14:26:25

标签: python popen argparse

我正在创建一个python脚本,它使用用户提供的参数来启动可执行文件:

parser = argparse.ArgumentParser()
parser.add_argument('-c', '--stringC', dest="stringC", help="stringC", type=str)
parser.add_argument('-f', '--stringF', dest="stringF", help="stringF", type=str)
parser.add_argument('-o', '--stringO', dest="stringO", help="stringO", type=str)
parser.add_argument('-d', '--stringD', dest="stringD", help="stringD", type=str)
parser.add_argument('-s', '--stringS', dest="stringS", help="stringS", type=str)
args = parser.parse_args()

command = 'executable-location'
statement = [command, '-c', stringC, '-f', stringF, '-o', stringO, '-d', stringD, '-s', stringS]
p = subprocess.Popen(statement)

问题是其中一些参数对于可执行文件是可选的,如果没有提供,程序将使用自己的默认值。因此,即使我想有时使用默认值,也会使用所有参数。

理想情况下,我只想为可执行文件提供已解析的参数。我试过了

statement = [command, args]
p = subprocess.Popen(statement2)

p = subprocess.Popen(args)

但是它给了我以下错误:

  

TypeError:'Namespace'对象不可迭代

希望有人可以帮助我。提前谢谢。

2 个答案:

答案 0 :(得分:0)

如果可行,最简单的解决方案是将程序默认值合并到解析器中。

# For example
parser.add_argument('-f', '--stringF', dest="stringF",
                    help="stringF", type=str,
                    default="-f's default)

然后您不必担心是否在参数列表中使用args.stringF

否则,您需要一次构建一个选项的命令列表。

statement = [command]
if args.stringF is not None:
    statement += ["-f", args.StringF]
# etc

答案 1 :(得分:0)

我不完全确定你要做什么,但可能会有所帮助:

定义一个解析器,有两种不同的默认值:

>>> import argparse
>>> parser=argparse.ArgumentParser()
>>> parser.add_argument('-f','--foo',default='FOO')
>>> parser.add_argument('-b','--bar',default=argparse.SUPPRESS)

解析没有任何参数的案例。请注意,生成的命名空间的值为foo(默认值),但bar没有值 - 因为SUPPRESS默认值。

>>> args=parser.parse_args([])
>>> print(args)
Namespace(foo='FOO')

args.foo会给出字符串'FOO'。但您也可以将命名空间转换为字典或元组列表

>>> print(vars(args))
{'foo': 'FOO'}
>>> print(vars(args).items())
[('foo', 'FOO')]

如果我给args命名空间提供了几个参数:

>>> args=parser.parse_args(['-f','val1','-b','val2'])
>>> print(args)
Namespace(bar='val2', foo='val1')

可以进行相同的字典和列表转换。

>>> print(vars(args).items())
[('foo', 'val1'), ('bar', 'val2')]

您可以选择args是否包含合理的默认值,或者对于用户未提供的参数是否包含任何值。默认defaultNone,也很容易测试(例如args.baz is None)。

构建一个简单的列表,如

['command', 'foo', 'val1', 'bar', 'val2']

应该是直截了当的。使用-f-b代替默认的dest名称需要更多的摆弄。