argparse
模块是标准库中最大的模块之一,拥有大量的配置选项。 本章只是演示了其中最基础的一些特性,帮助你入门。同时我也不建议使用它来在大量的生产环境上使用,因为我们有更好的选择, 一个第三模块 Plumbum
。我会在后面的章节介绍它。
一、基本步骤
为了解析命令行选项
你首先要创建一个 ArgumentParser
实例, 并使用 add_argument()
方法声明你想要支持的选项。
无意义的示例
必须一个py 文件 prog.py
, 并写入如下内容
import argparse
parser = argparse.ArgumentParser()
parser.parse_args()
试着在命令行里执行如下代码
$ python3 prog.py --help
usage: prog.py [-h]
optional arguments:
-h, --help show this help message and exit
可以看到,即使没有做太多设置,这个脚本已经实现了命令行工具了,并且默认就会有
--help
参数。
--help
也可以简写为-h
二、添加必须的位置参数
位置参数就是,必须为程序提供的,并且不需要使用 -
和 --
。
继续编辑我们的 prog.py
文件。
这次我们可以使用实例的 add_argument()
函数来添加一个位置参数。
这个位置参数是必须的,不给其传参,将会抛出一个错误提示。
import argparse
parser = argparse.ArgumentParser()
parser.add_argument("show")
args = parser.parse_args()
print(args.show)
上面的代码中, 字符串的 'show' 被传给
add_argument()
方法。
最后他会变成实例的一个属性,用来接收在命令行里传入的实际的值。
最后一行我们打印了这个属性,也就可以实现打印出命令行里传入的实际的值了。
我们来执行一下
$ python3 prog.py hello
hello
这个时候使用 --help
,你会发现帮助信息并没有表明目前的这个位置参数是用来做什么的。
$ python3 prog.py --help
usage: prog.py [-h] show
positional arguments:
show
optional arguments:
-h, --help show this help message and exit
所以,接下来我们就来添加位置参数的帮助信息
三、 使用 help
添加帮助信息
$ cat prog.py
import argparse
parser = argparse.ArgumentParser()
parser.add_argument("show", help="打印出你输入的字符串")
args = parser.parse_args()
print(args.show)
再次执行,会看到我们添加的帮助信息
$ python3 prog.py -h
usage: prog.py [-h] show
positional arguments:
show 打印出你输入的字符串
optional arguments:
-h, --help show this help message and exit
四、添加更多的逻辑
我们可以在执行了 parser.parse_args()
之后,添加更多的逻辑,用于实现更多的功能。
比如,下面的示例计算 2
的任意次方。
import argparse
parser = argparse.ArgumentParser()
parser.add_argument("square",
type=int,
help="打印出 2 的幂值, 要求传入一个整数")
args = parser.parse_args()
print(2 ** args.square)
这里因为是算术运算,所以需要用
type=int
把传入的参数声明为整型。
执行结果如下:
$ python3 power.py 4
16
五、制作一个 copy
命令行工具
为了展示位置参数(Positional arguments),下面写一个cp.py
,实现简单的文件复制功能。
import argparse
import shutil
def _parse_args():
parser = argparse.ArgumentParser()
parser.add_argument(
"source",
help="指定要复制的文件,支持相对路径和绝对路径",
)
parser.add_argument(
"target",
help="指定要复制的路径,包括拷贝后的文件名",
)
return parser.parse_args()
if __name__ == '__main__':
args = _parse_args()
shutil.copy(src=args.source, dst=args.target)
cp.py
命令后,第一个参数被识别为source
,第二个参数被识别为target
,然后执行复制。在parse_args()
之后,sys.argv
的参数列表,变成了结构化的args
。
(args
的类型,是一个<class 'argparse.Namespace'>
)。
如果执行python cp.py cp.py cp2.py
,那么不会有任何显示信息,成功执行复制操作。
如果多一个或者少一个参数呢?
$ python3 cp.py one.py
usage: cp.py [-h] source target
cp.py: error: the following arguments are required: target
$ python3 cp.py one.py two.py three.py
usage: cp.py [-h] source target
cp.py: error: unrecognized arguments: three.py
这就比直接使用sys.argv
的可靠性要高多了。
注意这里并没有对源文件是否存在进行检测。
六、可选参数
可选参数就是可有可无的参数,一般用 -
或者 --
表示。
可选参数就是需要使用 -
或者 --
后面紧跟的是一个关键字。比如 -h
也称为短参数 ,--help
也称为长参数。
这个两种可以同时存在于程序中,也可以只出现一种。
让我们继续改写 cp.py
程序,让其具有查看版本的参数 -v
和 --version
。
import argparse
import shutil
def _parse_args():
parser = argparse.ArgumentParser()
parser.add_argument(
"source",
help="指定要复制的文件,支持相对路径和绝对路径",
)
parser.add_argument(
"target",
help="指定要复制的路径,包括拷贝后的文件名",
)
parser.add_argument(
'-v',
'--version',
action='version', # 遇到参数时的动作,默认值 store
version='%(prog)s 1.1', ## 实际打印出来的内容
help='查看程序版本',
)
return parser.parse_args()
if __name__ == '__main__':
args = _parse_args()
shutil.copy(src=args.source, dst=args.target)
$ python3 cp.py -v
cp.py 1.1 1.1
针对上面的示例说一下
action 用于当使用某一个参数时,将会触发的动作,这些动作是内置好的
这里的 version 就是其中一个动作
vervion 其对应的值就是,使用 -v 参数后要显示的内容,其中 `prog` 是内置的一个变量,其值是脚本文件名。
action='version' 和 version 通常一起配套使用
关于 action
可选的内置好的值
-
store
保存参数值,可能会先将参数值转换成另一个数据类型。若没有显式指定动作,则默认为该动作,会把参数的值保存在一个变量上。 -
store_const
保存一个被定义为参数规格一部分的值,而不是一个来自参数解析而来的值。这通常用于实现非布尔值的命令行标记。 -
store_ture
/store_false
保存相应的布尔值。这两个动作被用于实现布尔开关, 比如linux
系统中好多命令经常会-R
参数,表示是否递归,使用这个参数表示为True
, 不使用为False
。 -
append
将值保存到一个列表中。若参数重复出现,则保存多个值。 -
append_const
将一个定义在参数规格中的值保存到一个列表中。 -
version
打印关于程序的版本信息,然后退出
在每个 add_argument()
调用中,dest
参数指定解析命令行传入的参数的变量名字。 help
参数被用来生成自定义的帮助信息。action
参数指定跟属性对应的处理逻辑, 通常的值为 store
,被用来存储某个值或将多个参数值收集到一个列表中。 下面的参数收集所有剩余的命令行参数到一个列表中。在本例中它被用来构造一个文件名列表:
parser.add_argument(dest='filenames',metavar='filename', nargs='*')
下面的参数根据参数是否存在来设置一个 Boolean
标志:
parser.add_argument('-v', dest='verbose', action='store_true',
help='verbose mode')
下面的参数接受一个单独值并将其存储为一个字符串:
parser.add_argument('-o', dest='outfile', action='store',
help='output file')
下面的参数说明允许某个参数重复出现多次,并将它们追加到一个列表中去。 required
标志表示该参数至少要有一个。-p
和 --pat
表示两个参数名形式都可使用。
parser.add_argument('-p', '--pat',metavar='pattern', required=True,
dest='patterns', action='append',
help='text pattern to search for')
最后,下面的参数说明接受一个值,但是会将其和可能的选择值做比较,以检测其合法性:
parser.add_argument('--speed', dest='speed', action='store',
choices={'slow','fast'}, default='slow',
help='search speed')
一旦参数选项被指定,你就可以执行 parser.parse()
方法了。 它会处理 sys.argv
的值并返回一个结果实例。 每个参数值会被设置成该实例中 add_argument()
方法的 dest
参数指定的属性值。
还很多种其他方法解析命令行选项。 例如,你可能会手动的处理 sys.argv
或者使用 getopt
模块。 但是,如果你采用本节的方式,将会减少很多冗余代码,底层细节 argparse
模块已经帮你处理了。 你可能还会碰到使用 optparse
库解析选项的代码。 尽管 optparse
和 argparse
很像,但是后者更先进,因此在新的程序中你应该使用它。
- action - 在命令行遇到此参数时要采取的基本操作类型。
- nargs - 应该使用的命令行参数的数量。
- const - 某些操作和nargs选择所需的常量值。
- default - 如果命令行中不存在参数,则生成的值。
- type - 应转换命令行参数的类型。
- choices - 参数允许值的容器。
- required - 是否可以省略命令行选项(仅限选项)。
- help - 对参数的作用的简要描述。
- metavar - 用法消息中参数的名称。
- dest - 要添加到返回的对象的属性的名称 parse_args()。