【问题标题】:What is the best way to customize help formatter for argparse.ArgumentParser为 argparse.ArgumentParser 自定义帮助格式化程序的最佳方法是什么
【发布时间】:2023-01-24 14:26:50
【问题描述】:

我正在使用 argparse.ArgumentParser 来解析参数和输出帮助文本。我想显示所有选项的默认值并设置输出的宽度。我当前的解决方案似乎有点乱七八糟。有人可以建议一种更好的方法来解决这个问题吗?我目前的做法是定义一个argparse.ArgumentDefaultsHelpFormatter的子类,然后修改__init__中的width属性。对更清洁的东西有什么想法吗?

# help class to set width of help to wrap at terminal width
class MyHelpFormatter(argparse.ArgumentDefaultsHelpFormatter):
    columns = -1

    def __init__(self, *args, **kwargs):
        if MyHelpFormatter.columns == -1:
            try:
                MyHelpFormatter.columns = os.get_terminal_size().columns
                if 'width' not in kwargs:
                    kwargs['width'] = MyHelpFormatter.columns
            except OSError:
                # not in a terminal
                pass
        super().__init__(*args, **kwargs)


# instantiate argument parser
parser = argparse.ArgumentParser(description='program description',
                                 formatter_class=MyHelpFormatter)

【问题讨论】:

  • 为什么你认为那是 hack? ArgumentDefaultsHelpFormatter 是主格式化程序的子类;为什么不再采取一步呢? argparse 就是这样设计的。
  • 对于一些应该非常小的东西来说,似乎有很多代码,例如,只是改变宽度。
  • 那是因为get_formatter 只将prog 传递给__Init__。我用过(或见过)formatter_class=lambda prog : self.formatter_class(prog=prog, widt=102)之类的东西。我忘记了细节,但我的想法是将 width 添加到通话中。但是你的子类给了你更多的灵活性。
  • argparse 开发人员更喜欢子类化以允许自定义,而不是提供许多初始化参数(然后必须作为属性或全局变量传递)。 ArgumentParser(和Action)已经采用了比大多数用户需要(或理解)更多的关键字参数。

标签: python argparse


【解决方案1】:

最后,由于冗长,我创建了一个名为 argparser.py 的简单 python 文件(注意多余的“r”),将它放在我的 python 路径中,现在我只使用它而不是 argparse。

'''
Extension to argparse to show default values for arguments and
print out help at proper width on screen.  Basically, it just adds the
MyHelpFormatter to the constructor for the argparse.ArgumentParser
class.

Example usage:
-------------------
import argparser

parser = argparser.ArgumentParser(description="Find and deal with autosave file")
parser.add_argument('-n', '--newer', type=int, default=0, help='how many days back to go, 0->forever')
args = parser.parse_args()
-------------------

Running this with -h would produce:

usage: <progname>.py [-h] [-n NEWER]

Find and deal with autosave file

optional arguments:
  -h, --help            show this help message and exit
  -n NEWER, --newer NEWER
                        how many days back to go, 0->forever (default: 0)

'''


import argparse
import os
import sys

if sys.version_info[0] < 3:
    raise RuntimeError('Need python3 or greater to use argparser.py')


class MyHelpFormatter(argparse.ArgumentDefaultsHelpFormatter):
    columns = -1

    def __init__(self, *args, **kwargs):
        if MyHelpFormatter.columns == -1:
            try:
                MyHelpFormatter.columns = os.get_terminal_size().columns
                if 'width' not in kwargs:
                    kwargs['width'] = MyHelpFormatter.columns
            except OSError:
                # not in a terminal
                pass
        super().__init__(*args, **kwargs)


class ArgumentParser(argparse.ArgumentParser):
    def __init__(self, *args, **kwargs):
        kwargs['formatter_class'] = MyHelpFormatter
        super().__init__(*args, **kwargs)

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-06-09
    • 2019-04-11
    • 2013-09-15
    • 1970-01-01
    • 1970-01-01
    • 2015-12-11
    相关资源
    最近更新 更多