python命令行参数的解析

BG11

Posted by Blue Geek on September 20, 2019

python命令行参数的解析

By 青衣极客 Blue Geek In 2019-09-20

在编写python程序的时候,如果参数是固定不动的可能就直接写入到代码中,如果是需要调整变动的,或者要提供多种可选择的功能时就需要在运行时指定参数。如果参数极多当然可以通过文件的方式来载入,但是在实际开发中发现,大多数时候需要调整的参数并不太多,却也不得不频繁变化。这时,命令行参数的解析就派上用场了,不仅会提高效率,而且显得更加专业。

python中提供命令行解析的模块是argparse,该模块基本完成支持了目前常用的对命令汗参数解析的需求。

1. 编写python文件

下面我们就一起看一下使用argparse进行参数解析的代码编写。

!cat ./code/test_argparse.py
# encoding: utf-8

import sys
import argparse

def main():
    args = argparse.ArgumentParser(description='Test argparse function')
    # 添加一个参数用于获取姓名
    args.add_argument('name', type=str, help='你的名字')
    # 添加一个参数用于获取年龄
    args.add_argument('age', type=int, help='你的年龄')
    # 添加一个参数用于获取身份证号
    args.add_argument('-i', "--id", type=str, dest='id', help='身份编码')
    # 添加一个参数用于获取性别,并限制选择范围
    args.add_argument("--sex", type=str, help='性别', default='男', choices=['男', '女'])
    # 添加一个参数用户获取其他参数,不要求存在,参数个数不限制
    args.add_argument('-o', '--other', type=str, dest='other', help='其他参数', required=False, nargs='*')
    # 解析参数
    args = args.parse_args()

    print('args.name = ', args.name)
    print('args.age = ', args.age)
    print('args.id = ', args.id)
    print('args.sex = ', args.sex)
    print('args.other = ', args.other)


if __name__ == '__main__':
    main()

其实命令参数分为两大类:位置参数和可选参数。其中位置参数是根据参数传入的位置确定的,因此必须完全指定,否则位置就无法确定而导致报错。而可选参数就要求宽松一些,可以不用传递,而使用设置的默认值,或者自动默认的空值。

2. 查看帮助信息

如果代码防止时间比较长,自己也忘记了传参的方式和内容,可以直接调用help参数来查看帮助信息。

!python3 ./code/test_argparse.py -h
usage: test_argparse.py [-h] [-i ID] [--sex {男,女}] [-o [OTHER [OTHER ...]]]
                        name age

Test argparse function

positional arguments:
  name                  你的名字
  age                   你的年龄

optional arguments:
  -h, --help            show this help message and exit
  -i ID, --id ID        身份编码
  --sex {男,女}           性别
  -o [OTHER [OTHER ...]], --other [OTHER [OTHER ...]]
                        其他参数

这些帮助信息是argparse模块根据代码中添加的参数自动生成的,当然也是可以手动定制的,但是不建议自行修改。从帮助信息可以很清晰地看出所有的参数,以及各个参数的说明和约束条件。

3. 完整传参

我们先来讲参数完整地传递一次看看会有什么表现。

!python3 ./code/test_argparse.py 张三 18 -i=12345678901 --sex  -o 12 34 5 67 
args.name =  张三
args.age =  18
args.id =  12345678901
args.sex =  女
args.other =  ['12', '34', '5', '67']

完整传参之后,姓名、号码和性别都是完全按照预期执行,其他参数被编入一个列表中。

4. 只传必要的参数

接下来,我们看一下不传那些可选的参数,只传必要的位置参数会是什么结果。

!python3 ./code/test_argparse.py 张三 18
args.name =  张三
args.age =  18
args.id =  None
args.sex =  男
args.other =  None

可以看出,姓名和年龄都正常传入,编码id由于缺失,所以使用自动默认的空值,性别使用了设置的默认男性,other参数也是空值。

5. 必要参数传输不完全

如果连必要的位置参数都传不完全的话,会是什么结果呢?下面就演示一下。

!python3 ./code/test_argparse.py 张三
usage: test_argparse.py [-h] [-i ID] [--sex {男,女}] [-o [OTHER [OTHER ...]]]
                        name age
test_argparse.py: error: the following arguments are required: age

与之前的描述一致,位置参数不完全就会报错,而且报错信息还会指出是哪个参数没有传递。不得不说这样的设计也是很贴心,完全考虑到了使用过程中可能出现的任何问题。

当然,这个模块可定制的功能还有很多,但是作为使用而言,很多定制的地方是不建议的。因为自动处理地已经很不错了,自行修改可能会使得整体风格不搭,而且让人困惑。

【青衣极客】公众号



COMMENT

博客评论区功能由Github Issue提供,提交Issue时请以本文标题为话题

"BG11-python命令行参数的解析"