Python 如何使argparse参数中的多个选项成为默认值,但一个或多个chocie是可选的?

Python 如何使argparse参数中的多个选项成为默认值,但一个或多个chocie是可选的?,python,argparse,Python,Argparse,我想在解析器中添加一个参数,其中可以从某个参数中选择多个选项。但是,默认情况下,我希望所有三个选项都在默认情况下运行,除非用户表示他或她只希望运行一个或两个可能的选项 import argparse if __name__ == "__main__": parser = argparse.ArgumentParser() parser.add_argument( "-o", "--output_type", choices= [

我想在解析器中添加一个参数,其中可以从某个参数中选择多个选项。但是,默认情况下,我希望所有三个选项都在默认情况下运行,除非用户表示他或她只希望运行一个或两个可能的选项

import argparse

if __name__ == "__main__":
    parser = argparse.ArgumentParser()

    parser.add_argument(
        "-o",
        "--output_type",
        choices= ['count', 'proportion', 'percentage'],
        default= 'count', 'proportion', 'percentage')

    args= parser.parse_args()

    if args.output_type == ['count','proportion','percentage']:
        ###do stuff
    elif args.output_type == 'percentage' or args.output_type == 'count' or args.output_type == 'proportion':
        ###do stuff
    else:
        ###raise error

但它似乎不能正常工作。可能是我的条件树设置不正确,但我不确定。有人能告诉我如何更好地组织这个吗?

当我尝试运行您的代码(来自我正在使用的python 2.7)时,它会在关键字arg之后给出
语法错误:非关键字arg
。因此,如果要将所有选项设置为默认值,可以使用
default
内置函数,只需设置
default=all
。其次,
args
应该在使用之前进行解析,即
args=parser.parse_args()


编辑:正如@hpaulj所说,
elif args.output\u type='percentage'或args.output\u type='count'或args.output\u type='proporty':
可以简化为
elif args.output\u type in['percentage',count',proportion']:

我希望以下能够有所帮助:

import argparse

if __name__ == "__main__":
    parser = argparse.ArgumentParser()

    parser.add_argument(
        "-o",
        "--output_type",
        choices = ['count', 'proportion', 'percentage'],
        default = all)

args = parser.parse_args()

if args.output_type == all:
    print "all"
elif args.output_type in ['percentage', 'count', 'proportion']:
    print "one"
else:
    print "error"

如果我按照发布的方式运行你的代码,我会得到一个语法错误

  File "stack44160281.py", line 10
    default= 'count', 'proportion', 'percentage')
SyntaxError: non-keyword arg after keyword arg
default='count'
可以,但是接下来的两个字符串不符合函数的参数规格

你可能是有意的

default= ['count', 'proportion', 'percentage']
但是现在我得到:
NameError:name'args'没有定义
您忘记了
args=parser.parse_args()

1436:~/mypy$ python stack44160281.py 
Namespace(output_type=['count', 'proportion', 'percentage'])
do default

1436:~/mypy$ python stack44160281.py -o count
Namespace(output_type='count')
do stuff
1437:~/mypy$ python stack44160281.py -o percentage
Namespace(output_type='percentage')
do stuff
1438:~/mypy$ python stack44160281.py -o wrong
usage: stack44160281.py [-h] [-o {count,proportion,percentage}]
stack44160281.py: error: argument -o/--output_type: invalid choice: 'wrong' (choose from 'count', 'proportion', 'percentage')
1438:~/mypy$ python stack44160281.py -h
usage: stack44160281.py [-h] [-o {count,proportion,percentage}]

optional arguments:
  -h, --help            show this help message and exit
  -o {count,proportion,percentage}, --output_type {count,proportion,percentage}
最后几行的缩进是错误的

在纠正所有这些事项(其中任何一项都应进行
close
投票)后(并添加诊断
print(args)
行)

elif
行可以压缩为:

elif args.output_type in ['percentage', 'count', 'proportion']:
if args.output_type in ['percentage', 'count', 'proportion']:
    print('do stuff')
else:
    print('do default')
default
几乎可以被任何字符串替换,例如
default='default'
如果args.output\u type=='default'
它甚至可以保留为默认值
None
,如果args.output\u type为None:,则使用
进行测试

您可以添加另一个选项,例如
'all'
,并将其用作
默认值。这将让您的用户提供该值

请注意,
选项
使我们无法进入
else
错误行

事实上,调度可以浓缩为:

elif args.output_type in ['percentage', 'count', 'proportion']:
if args.output_type in ['percentage', 'count', 'proportion']:
    print('do stuff')
else:
    print('do default')
因为该值保证是
选项之一
默认值

注意:此设置不是一个选择题。您的用户仍然必须只提供其中一个选项,而不是几个选项。通过改变
nargs
action
我们可以改变这一点。我们还需要改变测试


如果
output\u type
具有
nargs='+'
参数,则
args.output\u type
将是一个列表。您可以使用以下方法测试特定列表:

if args.output_type == ['one', 'two']:
但是,如果用户给你的是
['two','one']

通常情况下,使用以下内容测试列表:

for value in args.output_type:
   if value in ['one', 'two']:
        <act>
   else if value in ['three']:
        <act>
   else:
        <act>
用于args.output\u类型中的值:
如果['1','2']中的值:
如果['three']中的值为else,则为:
其他:
如果要同时测试这两个值,可以使用
,因此顺序无关紧要


有很多方法可以组织逻辑。这取决于这些值对您意味着什么。

当您说“它似乎格式不正确”时,您的意思是什么?“当你试图运行代码时,代码是否会给你一个错误,或者它是否运行但没有按你所希望的方式运行?”bouteillebleu稍微弄错了这些词。我已经修正了上面的错误。我的意思是代码不起作用。啊,好吧,这是有道理的。它会给你一个错误信息吗?如果是这样的话,在帖子中添加错误消息将有助于人们为您解决这个问题。@bouteillebleu很遗憾,因为我的计算机与存储代码的计算机不同,我现在无法访问特定的错误。我可以尝试在这台计算机上重新创建一个简化版本。谢谢!另外,还有一个简单的附加问题,因为我们在参数中设置了默认值,这意味着我们在运行参数时不需要在命令行中指定参数,对吗?如果要使用默认值运行参数,则无需指定。
all
是一个内置函数。
elif args.output\u键入['percentage',count',proportion']:
较短。@hpaulj虽然执行
elif args.output\u键入['percentage'、'count'、'proportion']:
较短,但它恐怕无法执行我想要的功能。我必须用这三个选项构建三个不同的dict,并且试图在前面描述的
elif
子句中指定要构建的dict对我来说是不实际的。非常感谢您的回答,但是你能告诉我我需要做些什么来处理
nargs
action
,以适应不止一个答案吗?你试过
nargs='+'
args.output\u type
应该是一个包含一个或多个字符串的列表。我确实尝试过,但它不起作用。它可以是一个选项,也可以是所有选项(当程序在命令行中运行时没有
-o
标志时,这是默认选项。我可能设置了错误的调度条件树。我是否应该向它添加额外的部分,例如
elif args.output\u type==['percentage','count']:…
,为了适应三种选择中的两种?是
argparse
输出有问题,还是您的条件树有问题?对于字符串列表,您必须更改测试。常见的方法是在列表上迭代,并测试每个元素。我想问题可能在我的条件树中。您认为我应该设置吗在args.output\u type:…
中为输出创建一个类似
的循环?