17

sys.argv运行程序时在 shell 命令行中接受参数。如何使这些参数可选?

我知道我可以使用try- except。但这会迫使您不插入额外的参数或插入所有额外的参数,除非您嵌套更多try-except这会使代码看起来更不可读。

编辑

假设我想要以下功能,我该如何实现?

$ python program.py add Peter 
'Peter' was added to the list of names.

这个add参数(而不是--add)是可选的,这样

$ python program.py

只是正常运行程序。

4

4 回答 4

9

编辑 以解决您的编辑,

import sys

sys.argv = sys.argv[1:]
names = []
while sys.argv and sys.argv[0] == 'add':
    #while the list is not empty and there is a name to add
    names.append(sys.argv[1])
    print sys.argv[1], 'was added to the list of names.'
    sys.argv = sys.argv[2:]

以下所有工作都与此有关

$ python program.py add Peter
Peter was added to the list of names.

$ python program.py add Peter add Jane
Peter was added to the list of names.
Jane was added to the list of names.

$ python program.py

如果在每个名称之前要求“添加”的好处是,如果在添加名称后还有其他要查找的参数,则可以。如果您想通过说python program.py add Peter Jane这可以通过一个相当简单的更改来传递多个名称

import sys

names = []
if len(sys.argv) > 2 and sys.argv[1] == 'add':
    names = sys.argv[2:]

for n in names:
    print n, 'was added to the list of names.'

原来的

似乎使用 optparse 之类的东西会更好。但是,由于sys.argv是一个列表,您可以检查它的长度。

arg1 = sys.argv[1] if len(sys.argv) > 1 else 0 # replace 0 with whatever default you want
arg2 = sys.argv[2] if len(sys.argv) > 2 else 0

然后使用 arg1 和 arg2 作为您的“可选”命令行参数。这将允许您传递 1、2 或 0 个命令行参数(实际上您可以传递超过 2 个,它们将被忽略)。这也假设参数有一个已知的顺序,如果你想使用标志,如-a后跟一个值,请查看 optparse http://docs.python.org/library/optparse.html?highlight=optparse#optparse

于 2012-08-07T21:13:02.527 回答
4

plac是其他答案中给出的标准库模块的替代方案。它允许通过注释定义命令行参数。从文档中,示例 8 演示了可选参数语法:

example8.py
def main(command: ("SQL query", 'option', 'q'), dsn):
    if command:
        print('executing %s on %s' % (command, dsn))
        # ...

if __name__ == '__main__':
    import plac; plac.call(main)

argparse 示例:

import argparse
parser = argparse.ArgumentParser()
parser.add_argument("--add", help="Add prefix to string")
args = parser.parse_args()

请注意,约定是将可选参数作为“--add”提供,而子命令作为“add”提供。argparse 中有一个子命令实现

于 2012-08-08T13:13:16.183 回答
2

您应该使用命令行解析器,例如 getopt 或argparse。这些允许您定义可选且具有默认值的选项。

于 2012-08-07T20:24:37.457 回答
2

作为对您问题的简单回答,您可以使用 可选参数sys.argv,但如果您预见到您的模块会扩展很多,您可能需要考虑另一个模块,argparse如其他地方所建议的那样。

这将不忽略任何参数,但之后允许任意数量的参数。

#!/usr/bin/env python

import sys

added = sys.argv[1:]
if added:
    for add in added:
        print("{0} was added to the list of names.".format(add))
$ ./test.py
$ ./test.py Peter
Peter was added to the list of names.

Of course you are not passing add Peter just Peter. But if that is acceptable, then this works.

My point is you can certainly do optional args with sys, and in fact for very simple scripts it is often not necessary to use argparse if that suffices!

于 2020-01-30T15:01:49.503 回答