Nar*_*the 8 python dynamic argparse subparsers
这是我想要做的:一个看起来像git命令行为的命令.无论是键入git commit还是git checkout,都没有相同的选项.但在我的情况下,我想提供基于参数值(文件名)的不同参数,如下所示:
>cmd file.a -h
usage: cmd filename [-opt1] [-opt2]
positional arguments:
filename file to process
optional arguments:
-opt1 do something on files of type 'a'
-opt2 do something else on files of type 'a'
>cmd file.b -h
usage: cmd filename [-opt3] [-opt4]
positional arguments:
filename file to process
optional arguments:
-opt3 do something on files of type 'b'
-opt4 do something else on files of type 'b'
Run Code Online (Sandbox Code Playgroud)
使用python和argparse可以做这种事情吗?
到目前为止我尝试的是:
parser = argparse.Argument_parser(prog='cmd')
subparsers = parser.add_subparsers()
parser.add_argument('filename',
help="file or sequence to process")
args = parser.parse_args(args=argv[1:])
sub_parser = subparsers.add_parser(args.filename, help="job type")
base, ext = os.path.splitext(args.filename)
if ext == 'a':
sub_parser.add_argument("-opt1", action='store_true')
sub_parser.add_argument("-opt2", action='store_true')
elif ext == 'b':
sub_parser.add_argument("-opt3", action='store_true')
sub_parser.add_argument("-opt4", action='store_true')
args = parser.parse_args(args=argv[1:])
Run Code Online (Sandbox Code Playgroud)
我不知道我是否应该使用子分析器或子分析器或组,我有点迷失在argparse提供的所有可能性中
Vyk*_*tor 23
当您查看parse_args()实现时,您会注意到它一次解析所有参数(它不yield用于连续生成状态),因此您必须在解析一半参数之前而不是之后准备您的结构.
从文档中的官方示例中,您应该在开始解析之前添加subparser,如下所示:
import argparse
parser = argparse.ArgumentParser(prog='PROG')
subparsers = parser.add_subparsers(help='sub-command help')
# create the parser for the "a" command
parser_a = subparsers.add_parser('a', help='a help')
parser_a.add_argument("--opt1", action='store_true')
parser_a.add_argument("--opt2", action='store_true')
# create the parser for the "b" command
parser_b = subparsers.add_parser('b', help='b help')
parser_b.add_argument("--opt3", action='store_true')
parser_b.add_argument("--opt4", action='store_true')
# parse some argument lists
print(parser.parse_args())
Run Code Online (Sandbox Code Playgroud)
并且输出(在命令行中),帮助很好地打印:
D:\tmp>s.py -h
usage: PROG [-h] {a,b} ...
positional arguments:
{a,b} sub-command help
a a help
b b help
optional arguments:
-h, --help show this help message and exit
Run Code Online (Sandbox Code Playgroud)
一个参数解析
D:\tmp>s.py a --opt1
Namespace(opt1=True, opt2=False)
Run Code Online (Sandbox Code Playgroud)
解析B参数
D:\tmp>s.py b
Namespace(opt3=False, opt4=False)
Run Code Online (Sandbox Code Playgroud)
还有args:
D:\tmp>s.py b --opt3
Namespace(opt3=True, opt4=False)
Run Code Online (Sandbox Code Playgroud)
运行一个在辩论中乙导致的错误:
D:\tmp>s.py b --opt2
usage: PROG [-h] {a,b} ...
PROG: error: unrecognized arguments: --opt2
Run Code Online (Sandbox Code Playgroud)
此外,如果您需要确定使用了哪个subparser,您可以添加dest=name到parser.add_subparsers()call(我认为在文档中没有正确强调):
subparsers = parser.add_subparsers(help='sub-command help', dest='subparser_name')
Run Code Online (Sandbox Code Playgroud)
结果如下:
D:\tmp>s.py b --opt3
Namespace(opt3=True, opt4=False, subparser_name='b')
Run Code Online (Sandbox Code Playgroud)
如果您需要动态创建参数(例如从昂贵的资源加载一些参数选项),您可以使用parse_known_args():
有时,脚本可能只解析一些命令行参数,将剩余的参数传递给另一个脚本或程序.在这些情况下,该
parse_known_args()方法可能是有用的.它的工作方式非常类似,parse_args()只是在存在额外参数时不会产生错误.相反,它返回一个包含填充命名空间和剩余参数字符串列表的两项元组.
毕竟,parse_args()只需检查尾随的纪念碑:
def parse_args(self, args=None, namespace=None):
args, argv = self.parse_known_args(args, namespace)
if argv:
msg = _('unrecognized arguments: %s')
self.error(msg % ' '.join(argv))
return args
Run Code Online (Sandbox Code Playgroud)
然后你可以重新执行另一个解析器argv,但是我可以想象一些可以解决这个问题的问题,在真正需要之前我不会推荐它.
| 归档时间: |
|
| 查看次数: |
5503 次 |
| 最近记录: |