检查是否设置了argparse可选参数


112

我想检查用户是否设置了可选的argparse参数。

我可以安全地使用isset检查吗?

像这样:

if(isset(args.myArg)):
    #do something
else:
    #do something else

这对于float / int / string类型参数是否起作用?

我可以设置一个默认参数并检查它(例如,设置myArg = -1,或为字符串““或“ NOT_SET”)。但是,我最终要使用的值仅在脚本的稍后部分计算。因此,我会将其默认设置为-1,然后稍后将其更新为其他内容。与仅检查该值是否由用户设置相比,这似乎有点笨拙。


1
将会isset()是什么(提示:Python不是PHP)?hasattr()也许是您的意思吗?为什么不配置argparse为选项设置默认值呢?
马丁·彼得斯

@MartijnPieters-是的,是的。所以我可以简单地检查一下是否(args.myArg):...
马德琳·文森特

Answers:


146

我认为,如果未提供可选参数(用指定--),None则将其初始化。因此,您可以使用进行测试is not None。请尝试以下示例:

import argparse as ap

def main():
    parser = ap.ArgumentParser(description="My Script")
    parser.add_argument("--myArg")
    args, leftovers = parser.parse_known_args()

    if args.myArg is not None:
        print "myArg has been set (value is %s)" % args.myArg

“是无”和“不是无”测试的工作完全符合我的期望和期望。谢谢。
马德琳·文森特

39
不幸的是,它不起作用,然后参数将其default定义为值。
kcpr

6
如果要设置default,则仍然可以设置nargs='?'并提供const值,如docs中所述。当arg不存在时,default使用arg,当arg给定w / o值时,则const使用,否则使用给定值。如果没有给定,则使用only defaultnargs='?'default如果没有给None定值,则使用w,否则给定值。
Ioannis Filippidis

如果你使用@IoannisFilippidis action= "store_true"action="store_const", const="yourconst"您无法使用该参数存储其他值。使用默认值时,这将不起作用。我自己从argparser中删除了所有默认值,并在另一个函数def defaults():中处理了所有默认值,在该函数中,我按照我想要的顺序混合了ConfigParser,ArgumentParser和默认值
m3nda

@ erm3nda我没有提到设置action。答案不使用action。您提到的动作被记录为以一种特定的方式表现(如您所观察到的)。虽然没有必要定义动作。
艾奥尼斯·菲利皮迪斯(Ooannis Filippidis)

37

正如@Honza所说,这is None是一个很好的测试。这是默认设置default,用户无法给您提供重复的字符串。

您可以指定另一个default='mydefaultvalue,然后进行测试。但是,如果用户指定该字符串怎么办?是否算作设置?

您也可以指定default=argparse.SUPPRESS。然后,如果用户不使用该参数,它将不会出现在args名称空间中。但是测试可能会更复杂:

args.foo # raises an AttributeError
hasattr(args, 'foo')  # returns False
getattr(args, 'foo', 'other') # returns 'other'

内部parser保留一个的列表seen_actions,并将其用于“必需”和“互斥”测试。但您无法使用parse_args


22

我认为使用该选项default=argparse.SUPPRESS最有意义。然后,而不是检查参数是否为,而是检查参数是否not Nonein为结果名称空间。

例:

import argparse

parser = argparse.ArgumentParser()
parser.add_argument("--foo", default=argparse.SUPPRESS)
ns = parser.parse_args()

print("Parsed arguments: {}".format(ns))
print("foo in namespace?: {}".format("foo" in ns))

用法:

$ python argparse_test.py --foo 1
Parsed arguments: Namespace(foo='1')
foo in namespace?: True
不提供参数:
$ python argparse_test.py
Parsed arguments: Namespace()
foo in namespace?: False

在Python 3.7.5(Anaconda)下,这对我不起作用。我得到了结果testfoo.py: error: argument --foo: expected one argument
Mike Wise

@MikeWise如果要不--foo带任何值使用(即1在我的示例中),则必须nargs=0add_argument函数中指定。
伊拉斯mus

我只是按照答案中的说明复制并粘贴您的代码。也许您应该编辑它?我最终action='store_true'在我的实际代码中使用了下面的答案。
Mike Wise

@MikeWise是否以以下身份运行脚本python argparse_test.py --foo 1
伊拉斯mus

11

您可以使用store_truestore_false参数操作选项检查可选传递的标志:

import argparse

argparser = argparse.ArgumentParser()
argparser.add_argument('-flag', dest='flag_exists', action='store_true')

print argparser.parse_args([])
# Namespace(flag_exists=False)
print argparser.parse_args(['-flag'])
# Namespace(flag_exists=True)

这样,您就不必担心按条件检查is not None。您只需检查TrueFalse。在此处阅读更多关于这些选项的信息


1
这无法解决是否知道是否设置了具有值的参数的问题。这里的主要问题是要知道args值是否来自defaul =“”或由用户提供。
m3nda

5

如果您的参数是位置参数(即,它没有“-”或“-”前缀,只有参数,通常是文件名),则可以使用nargs参数执行此操作:

parser = argparse.ArgumentParser(description='Foo is a program that does things')
parser.add_argument('filename', nargs='?')
args = parser.parse_args()

if args.filename is not None:
    print('The file name is {}'.format(args.filename))
else:
    print('Oh well ; No args, no problems')

3

这是我的解决方案,看看我是否正在使用argparse变量

import argparse

ap = argparse.ArgumentParser()
ap.add_argument("-1", "--first", required=True)
ap.add_argument("-2", "--second", required=True)
ap.add_argument("-3", "--third", required=False) 
# Combine all arguments into a list called args
args = vars(ap.parse_args())
if args["third"] is not None:
# do something

这可能会使我对上面的答案有更深入的了解,而我使用该答案并对其进行了修改以使其适合我的程序。


0

为了解决@kcpr对@Honza Osobne的(当前接受的)答案的评论

不幸的是,它不起作用,然后参数将其定义为默认值。

首先可以通过将参数与 Namespace提供default=argparse.SUPPRESS选项对象abd(请参见@hpaulj和@Erasmus Cedernaes的答案以及此python3 doc),如果未提供参数,则将其设置为默认值。

import argparse

parser = argparse.ArgumentParser()
parser.add_argument('--infile', default=argparse.SUPPRESS)
args = parser.parse_args()
if 'infile' in args: 
    # the argument is in the namespace, it's been provided by the user
    # set it to what has been provided
    theinfile = args.infile
    print('argument \'--infile\' was given, set to {}'.format(theinfile))
else:
    # the argument isn't in the namespace
    # set it to a default value
    theinfile = 'your_default.txt'
    print('argument \'--infile\' was not given, set to default {}'.format(theinfile))

用法

$ python3 testargparse_so.py
argument '--infile' was not given, set to default your_default.txt

$ python3 testargparse_so.py --infile user_file.txt
argument '--infile' was given, set to user_file.txt

0

很简单,在通过“ args = parser.parse_args()”定义args变量后,它也包含args子集变量的所有数据。要检查是否设置了变量或假设使用的是'action =“ store_true” ...

if args.argument_name:
   # do something
else:
   # do something else
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.