我需要在Python中动态创建参数列表。我已经创建了一个脚本来演示这个,名为args.py,如下所示:
#!/usr/bin/python
import argparse
parser = argparse.ArgumentParser()
parser.add_argument('-args_file', default = 'args.txt')
with open(parser.parse_args().args_file, 'r') as f:
args = f.readlines()
for arg in args:
parser.add_argument('-' + arg.strip())
dynamic_args = parser.parse_args()
print dynamic_args
我在同一文件夹中也有一个文本文件,名为args.txt,如下所示:
arg1
arg2
arg3
正如预期的那样,运行没有参数的args.py会导致:
Namespace(arg1=None, arg2=None, arg3=None, args_file='args.txt')
然而,我遇到的问题是使用-h参数运行我的脚本。我想帮助显示args_file中的参数,如下例所示:
usage: args.py [-h] [-args_file ARGS_FILE] [-arg1 ARG1] [-arg2 ARG2]
[-arg3 ARG3]
我所看到的是:
usage: args.py [-h] [-args_file ARGS_FILE]
此外,如果我以交互方式运行脚本(即python -i arg.py),并在交互式提示符下键入命令“parser.print_usage()”,我会得到想要的响应(显示-argN参数)。此外,输入“arg.py -arg1 1”或“arg.py arg1 1”会导致“无法识别的参数”。
我已经尝试了所有我能想到的东西,但到目前为止我还没有成功。任何Python爱好者都有任何建议吗?
答案 0 :(得分:6)
正如Martjin所指出的,你可以在第一次省略解析器的帮助。另一件事是第一次使用parse_known_args
,所以你只需要解析args_file。
在这种情况下,我喜欢通过为第一个解析使用一次性解析器和最终解析的完整解析器来保持清晰:
import argparse
argfile_parser = argparse.ArgumentParser(add_help=False)
full_parser = argparse.ArgumentParser()
argfile_parser.add_argument('-args_file', default = 'args.txt')
full_parser.add_argument('-args_file', default = 'args.txt')
with open(argfile_parser.parse_known_args()[0].args_file, 'r') as f:
for arg in f:
full_parser.add_argument('-' + arg.strip())
dynamic_args = full_parser.parse_args()
print dynamic_args
为了进行测试,我添加了一个文件args2.txt
:
argA
argB
argC
我认为结果就是你要找的东西:
lap:~$ python tmp.py -h
usage: tmp.py [-h] [-args_file ARGS_FILE] [-arg1 ARG1] [-arg2 ARG2]
[-arg3 ARG3]
optional arguments:
-h, --help show this help message and exit
-args_file ARGS_FILE
-arg1 ARG1
-arg2 ARG2
-arg3 ARG3
lap:~$ python tmp.py -args_file args2.txt
Namespace(argA=None, argB=None, argC=None, args_file='args2.txt')
lap:~$ python tmp.py -h -args_file args2.txt
usage: tmp.py [-h] [-args_file ARGS_FILE] [-argA ARGA] [-argB ARGB]
[-argC ARGC]
optional arguments:
-h, --help show this help message and exit
-args_file ARGS_FILE
-argA ARGA
-argB ARGB
-argC ARGC
lap:~$ python tmp.py -arg1 foo
Namespace(arg1='foo', arg2=None, arg3=None, args_file='args.txt')
lap:~$ python tmp.py -args_file args2.txt -argA bar
Namespace(argA='bar', argB=None, argC=None, args_file='args2.txt')
答案 1 :(得分:0)
根据 Hazen 的回答,使用 parents
选项更容易。
https://docs.python.org/3/library/argparse.html#parents
import argparse
argfile_parser = argparse.ArgumentParser(add_help=False)
argfile_parser.add_argument('-args_file', default = 'args.txt')
full_parser = argparse.ArgumentParser(parents=[argfile_parser])
with open(argfile_parser.parse_known_args()[0].args_file, 'r') as f:
for arg in f:
full_parser.add_argument('-' + arg.strip())
dynamic_args = full_parser.parse_args()
print dynamic_args