Argparse:在'--help'中包含默认值的方法?

JS.*_*JS. 265 python argparse

假设我有以下argparse片段:

diags.cmdln_parser.add_argument( '--scan-time',
                     action  = 'store',
                     nargs   = '?',
                     type    = int,
                     default = 5,
                     help    = "Wait SCAN-TIME seconds between status checks.")
Run Code Online (Sandbox Code Playgroud)

目前,--help退货:

usage: connection_check.py [-h]
                             [--version] [--scan-time [SCAN_TIME]]

          Test the reliability/uptime of a connection.



optional arguments:
-h, --help            show this help message and exit
--version             show program's version number and exit
--scan-time [SCAN_TIME]
                    Wait SCAN-TIME seconds between status checks.
Run Code Online (Sandbox Code Playgroud)

我更喜欢这样的东西:

--scan-time [SCAN_TIME]
                    Wait SCAN-TIME seconds between status checks.
                    (Default = 5)
Run Code Online (Sandbox Code Playgroud)

偷看帮助格式化程序代码显示有限的选项.是否有一种聪明的方式来argparse--scan-time类似的方式打印默认值,或者我应该只是help格式化子类?

Mar*_*ers 394

使用argparse.ArgumentDefaultsHelpFormatter格式化程序:

parser = argparse.ArgumentParser(
    # ... other options ...
    formatter_class=argparse.ArgumentDefaultsHelpFormatter)
Run Code Online (Sandbox Code Playgroud)

引用文档:

另一个可用的格式化程序类ArgumentDefaultsHelpFormatter将添加有关每个参数的默认值的信息.

请注意,这仅适用于定义了帮助文本的参数 ; 没有help一个参数值,所以注意添加信息.

扫描时间选项的确切输出将变为:

  --scan-time [SCAN_TIME]
                        Wait SCAN-TIME seconds between status checks.
                        (default: 5)
Run Code Online (Sandbox Code Playgroud)

  • 您可以将`default`设置为`SUPPRESS`:`default = argparse.SUPPRESS`.请注意,在这种情况下,如果省略该参数,则不会向命名空间结果添加任何属性,请参阅[default` documentation](http://docs.python.org/2/library/argparse.html#default). (12认同)
  • 我可以控制只有带有显式`default =`的参数显示默认值吗?因为我不喜欢'默认:无'文本. (9认同)
  • @AzorAhai-him- 创建一个新类,对两者进行子类化并将其用作格式化程序;例如 `class RawTextArgumentDefaultsHelpFormatter(argparse.RawTextHelpFormatter, argparse.ArgumentDefaultsHelpFormatter): pass`, `parser = argparse.ArgumentParser(..., formatter_class=RawTextArgumentDefaultsHelpFormatter)`。这两个变体覆盖了基本帮助格式化程序的两个不同方面,因此可以轻松组合。 (7认同)
  • @David我遇到了同样的问题.在`add_argument`中添加`help`参数,这应该有效. (3认同)
  • 请注意,您还需要为每个创建的子分析器指定此项. (2认同)
  • 如果我已经设置了“formatter_class”,该怎么办? (2认同)

小智 167

添加'%(default)'到help参数以控制显示的内容.

parser.add_argument("--type", default="toto", choices=["toto","titi"],
                              help = "type (default: %(default)s)")
Run Code Online (Sandbox Code Playgroud)

  • 不要忘记在格式化字符串中包含变量"type" - 例如,字符串为"%(默认)s",数字为"%(默认)d". (19认同)
  • 我喜欢这个选项,因为我已经使用了format_class = argparse.RawTestHelpFormatter并且不喜欢用OOP放屁. (8认同)
  • 我更喜欢这个解决方案,它简单得多,而且我不必显式处理没有默认值的参数。 (5认同)

Cir*_*四事件 9

包装类

这是迄今为止我发现的最可靠和干燥的方法,它们都显示默认值并同时使用另一个格式化程序argparse.RawTextHelpFormatter:

#!/usr/bin/env python3

import argparse

class ArgumentParserWithDefaults(argparse.ArgumentParser):
    def add_argument(self, *args, help=None, default=None, **kwargs):
        if help is not None:
            kwargs['help'] = help
        if default is not None and args[0] != '-h':
            kwargs['default'] = default
            if help is not None:
                kwargs['help'] += ' Default: {}'.format(default)
        super().add_argument(*args, **kwargs)

parser = ArgumentParserWithDefaults(
    formatter_class=argparse.RawTextHelpFormatter
)
parser.add_argument('-a', default=13, help='''my help
for a''')
parser.add_argument('-b', default=42, help='''my help
for b''')
parser.add_argument('--no-default', help='''my help
for no-default''')
parser.add_argument('--no-help', default=101)

parser.print_help()
print()
print(parser.parse_args())
Run Code Online (Sandbox Code Playgroud)

输出:

usage: main.py [-h] [-a A] [-b B] [--no-default NO_DEFAULT]
               [--no-help NO_HELP]

optional arguments:
  -h, --help            show this help message and exit
  -a A                  my help
                        for a Default: 13
  -b B                  my help
                        for b Default: 42
  --no-default NO_DEFAULT
                        my help
                        for no-default
  --no-help NO_HELP

Namespace(a=13, b=42, no_default=None, no_help=101)
Run Code Online (Sandbox Code Playgroud)

ArgumentDefaultsHelpFormatter+ RawTextHelpFormatter多重继承

多重继承只是工作,但它似乎不是公共API:

#!/usr/bin/env python3

import argparse

class RawTextArgumentDefaultsHelpFormatter(
        argparse.ArgumentDefaultsHelpFormatter,
        argparse.RawTextHelpFormatter
    ):
        pass

parser = argparse.ArgumentParser(
    formatter_class=RawTextArgumentDefaultsHelpFormatter
)
parser.add_argument('-a', default=13, help='''my help
for a''')
parser.add_argument('-b', default=42, help='''my help
for b''')
parser.print_help()
Run Code Online (Sandbox Code Playgroud)

输出:

usage: a.py [-h] [-a A] [-b B]

optional arguments:
  -h, --help  show this help message and exit
  -a A        my help
              for a (default: 13)
  -b B        my help
              for b (default: 42)
Run Code Online (Sandbox Code Playgroud)

它只是起作用,因为我们可以从源https://github.com/python/cpython/blob/v3.6.5/Lib/argparse.py#L648中轻松地看到:

  • RawTextHelpFormatter 器物 _split_lines
  • ArgumentDefaultsHelpFormatter 器物 _get_help_string

所以我们可以猜测它们会很好地协同工作.

但是,这似乎不是公共API,也不是方法formatter_class,因此我认为目前没有公共API方法.argparsedocstring说:

本模块中的所有其他类都被视为实现细节.(另请注意,HelpFormatter和RawDescriptionHelpFormatter仅被视为公共对象名称 - 格式化程序对象的API仍被视为实现细节.)

另请参阅:自定义argparse帮助消息

在Python 3.6.5上测试.


exq*_*quo 7

能够自动default在帮助输出中包含值通常很有用,但仅限于显式指定的值(使用default=..)。已经提到的方法在这方面存在一些缺点:

  • ArgumentDefaultsHelpFormatter 方法打印出(default: None)每个未明确指定默认值的参数以及(default: False)“flags”( action='store_true')。这会使帮助输出变得混乱。为了避免这种情况,default=argparse.SUPPRESS需要为每个这样的参数手动添加。

  • '%(default)s' 方法help需要手动将其添加到我们希望在帮助中打印的所有参数字符串中。

这两种方法最终都需要手动干预才能仅打印出“正确”的默认值。自动执行此操作的一种方法是增强 来ArgumentDefaultsHelpFormatter忽略Nones 和Falses 默认值:

class ExplicitDefaultsHelpFormatter(argparse.ArgumentDefaultsHelpFormatter):
    def _get_help_string(self, action):
        if action.default is None or action.default is False:
            return action.help
        return super()._get_help_string(action)
Run Code Online (Sandbox Code Playgroud)

用它代替ArgumentDefaultsHelpFormatter

parser = argparse.ArgumentParser(
        formatter_class=ExplicitDefaultsHelpFormatter
                )
Run Code Online (Sandbox Code Playgroud)

default这将仅打印帮助输出中明确设置的值。

注意:如果参数的默认值显式设置为Noneor False,则该类的帮助中不会显示该参数;如果您希望在帮助输出中添加该参数的%(default)s字符串。help