我正在努力合并一些字符串替换,目前使用 sys.argv[i]
将参数传递给我的脚本 . 到目前为止,我发现文档相对不清楚 .
我的代码目前的工作方式是
filename.py -param_to_replace new_param_value
(我还可以包含多个参数来替换)
然后由此处理
if len(sys.argv) > 1:
for i in range((len(sys.argv)-1) / 2):
params[sys.argv[1+2*i].split('-')[1]] = float(sys.argv[1+2*i+1])
其中params是一组已定义参数的名称 .
我想我应该能够使用docopt,但到目前为止我所拥有的更像是
"""Docopt test
Usage:
filename.py --param_name1 <val> --param_name2 <val>
filename -h | --help
filename --version
Options:
-h --help Show this screen.
--param_name1 Change some param we call param_name1, all other params changed in similar way
"""
from docopt import docopt
if __name__ == '__main__':
arguments = docopt(__doc__, version='filename 1.0')
print(arguments)
但这并未传递任何内容,似乎是官方文档中提供的详细信息的结尾 . 有更熟悉docopt的人是否知道如何更有效地传递命令行参数?或者我应该在此之后用“arguments”替换sys.argv?
谢谢!
4 回答
而不是使用
docopt
(这无论如何都很棒),如果你只是想 Build 一个-param
的字典:value
,因为docopt会返回你可以用字典理解来做到这一点(我想以比你现在正在做的更容易理解的方式) ):然后测试一下:
我刚刚意识到
__doc__
正在做什么(见我的评论) .加载模块时,会将初始三重引用字符串分配给其
__doc__
变量 . 通常这是各种'help'包可以使用的文档 . 函数和类也有__doc__
. 对于docopt
使用,它应该模拟命令行解析器的help
显示 .该
line将此
__doc__
字符串传递给docopt
函数(或类) . 这推断出你想接受的参数,解析sys.argv
,并返回一个字典arguments
.在您的示例中,使用行是:
如果你用脚本调用脚本,我希望如此
arguments
将是一个字典,看起来像:和
arguments['param_name1']
应该返回'foo'您当前的代码显然试图解析输入,如
并执行
我希望
docopt
版本会在输入时产生错误,但我不知道它处理错误的细节 .Better solution than if name == 'main' twice in Python script是使用
python
docopt
的较长示例 .argparse版本
这是一个
argparse
脚本,我认为它的行为就像你的sys.argv
解析一样 . 它在params
字典中定义了一组基于argparse
参数的条目,并且应该返回兼容的字典 .生产环境 :
这可能会以相同的方式工作:
看起来你的docopt语法有问题 . 对我来说,使用web docopt tool计算docopt语法很有帮助 . 该设置可以很容易地快速迭代语法,看看它是否会产生一个对我的程序有用的结构 .
我把你的语法放在here中,带有参数
--param_name1 foo --param_name2 bar
并得到了这个结果:在第一部分中,您指定了:
Usage: filename.py --param_name1 <val> --param_name2 <val>
. 请注意,您在2个不同的位置使用<val>
,这意味着只填充第2个值 . 在第二部分中,您再次指定:Options: --param_name1
,这是多余的,因为您已在使用部分中指定了相同的--param_name1
. 论证应该在一个但不是两个部分 .Here是一个简化的语法:
使用
--old=foo --new=bar
解析的结果是:或者完全删除开关名称,只使用位置参数 . This可以更容易地预测要替换的多个参数 .
使用
bar foo baz
参数,这是解析的结构:我只是blogged关于我有多喜欢docopt,所以我希望你能克服最初的理解障碍 .
所以我想我会回到这个,因为我意识到我从未关闭过主题并发布了答案 . 传递参数的正确方法如下:
似乎只有一些使用问题,这在代码中清除了 .