您应该如何使用 argparse 来选择要执行的操作并将参数传递给它?

How should you use argparse to choose which action to perform and pass arguments to it?

我想使用 argparse 库来解析一些参数,但我正在努力找出在无数种指定参数的方法中,哪种方法是在几个操作之间进行选择的最简单方法。不同的动作需要不同数量的参数。

鉴于以下调用,我希望得到以下输出:

> python MyClass.py action1 foo
Action 1: 12345 - foo

> python MyClass.py action2 20 30
Action 2: 12345 - 20 30

以下似乎有效:

import argparse

class MyClass:
    def __init__(self, someVar):
        self.someVar = someVar

    def Action1(self, intToPrint):
        print("Print 1: %d - %s"%(self.someVar,intToPrint))

    def Action2(self, firstNum, firstString):
        print("Print 2: %d - %d %s"%(self.someVar,firstNum, firstString))

def CallAction1(mc, args):
    mc.Action1(args.intToPrint)

def CallAction2(mc, args):
    mc.Action2(args.firstNum, args.firstString)

def Main():
    parser = argparse.ArgumentParser(prog='PythonArgumentParsing.py')
    subparsers = parser.add_subparsers(help='commands')

    action1Group = subparsers.add_parser('action1', help='action 1 help')
    action1Group.add_argument('intToPrint', type=str)
    action1Group.set_defaults(func=CallAction1)

    action2Group = subparsers.add_parser('action2', help='action 1 help')
    action2Group.add_argument('firstNum', type=int)
    action2Group.add_argument('firstString', type=str)
    action2Group.set_defaults(func=CallAction2)

    args = parser.parse_args()
    someVar = 12345
    mc = MyClass(someVar)
    args.func(mc, args)

if __name__ == "__main__":
    Main()

...但是必须创建一个 CallAction 来传递来自解析器的参数似乎有点笨拙。

有什么办法可以解决这个问题吗?

我了解到您只是因为需要编写将 args 命名空间转换为方法调用的位置参数的 Call_Action... 函数而感到困扰。

使用关键字参数可能会消除这种需要。以下尚未测试:

def Action1(self, intToPrint=None, **kwargs):
    print("Print 1: %d - %s"%(self.someVar,intToPrint))

def Action2(self, firstNum=None, firstString=None, **kwargs):
    print("Print 2: %d - %d %s"%(self.someVar,firstNum, firstString))
...
action1Group.set_defaults(func=MyClass.Action1)
...
args.func(mc, **vars(args))

如果我做对了,我可以将整个 vars(args) 字典传递给该方法。它会使用它需要的参数,并忽略其余的。

argparse 大量使用 **kwargs 传递参数的方法。