Skip to content

15 argparse命令行参数

你写了个Python脚本,想让用户通过命令行传参数进去——python train.py --epochs 10 --lr 0.001。用sys.argv自己解析太麻烦,argparse就是干这个的,它是Python标准的命令行参数解析库。

一、快速开始

1.1 最简用法

python
import argparse

parser = argparse.ArgumentParser(description="一个简单的命令行工具")
parser.add_argument("name", help="你的名字")
args = parser.parse_args()

print(f"你好, {args.name}!")

运行:

bash
python hello.py 大志
# 你好, 大志!

python hello.py --help
# usage: hello.py [-h] name
#
# 一个简单的命令行工具
#
# positional arguments:
#   name        你的名字
#
# options:
#   -h, --help  show this help message and exit

1.2 可选参数

python
import argparse

parser = argparse.ArgumentParser()
parser.add_argument("--name", "-n", default="World", help="你的名字")
parser.add_argument("--verbose", "-v", action="store_true", help="详细输出")
args = parser.parse_args()

if args.verbose:
    print(f"详细模式开启")
print(f"你好, {args.name}!")

运行:

bash
python hello.py --name 大志 --verbose
# 详细模式开启
# 你好, 大志!

python hello.py -n 大志 -v
# 详细模式开启
# 你好, 大志!

二、add_argument详解

2.1 参数类型

python
import argparse

parser = argparse.ArgumentParser()
parser.add_argument("name", type=str, help="姓名")
parser.add_argument("age", type=int, help="年龄")
parser.add_argument("score", type=float, help="分数")
args = parser.parse_args()

print(f"{args.name}, {args.age}岁, {args.score}分")
bash
python test.py 大志 28 95.5
# 大志, 28岁, 95.5分

2.2 限制选项

python
import argparse

parser = argparse.ArgumentParser()
parser.add_argument("--level", choices=["debug", "info", "warning", "error"], 
                    default="info", help="日志级别")
args = parser.parse_args()

print(f"日志级别: {args.level}")
bash
python test.py --level debug   # OK
python test.py --level fatal   # error: argument --level: invalid choice: 'fatal'

2.3 必选可选参数

python
import argparse

parser = argparse.ArgumentParser()
parser.add_argument("--config", "-c", required=True, help="配置文件路径")
args = parser.parse_args()

2.4 布尔参数

python
import argparse

parser = argparse.ArgumentParser()
parser.add_argument("--verbose", "-v", action="store_true", help="详细模式")
parser.add_argument("--quiet", "-q", action="store_false", help="安静模式")
args = parser.parse_args()

print(f"verbose: {args.verbose}")  # True或False
print(f"quiet: {args.quiet}")      # True或False

2.5 计数参数

python
import argparse

parser = argparse.ArgumentParser()
parser.add_argument("-v", "--verbose", action="count", default=0, help="详细级别")
args = parser.parse_args()

print(f"详细级别: {args.verbose}")
bash
python test.py          # 详细级别: 0
python test.py -v       # 详细级别: 1
python test.py -vv      # 详细级别: 2
python test.py -vvv     # 详细级别: 3

2.6 多值参数

python
import argparse

parser = argparse.ArgumentParser()

# 接受多个值
parser.add_argument("--files", nargs="+", help="文件列表")
# nargs="+":至少1个
# nargs="*":0个或多个
# nargs="?":0个或1个
# nargs=N:精确N个

args = parser.parse_args()
print(args.files)
bash
python test.py --files a.txt b.txt c.txt
# ['a.txt', 'b.txt', 'c.txt']

三、参数分组

3.1 参数组

python
import argparse

parser = argparse.ArgumentParser(description="Agent训练工具")

# 输入参数组
input_group = parser.add_argument_group("输入参数")
input_group.add_argument("--data", required=True, help="数据文件路径")
input_group.add_argument("--config", help="配置文件路径")

# 训练参数组
train_group = parser.add_argument_group("训练参数")
train_group.add_argument("--epochs", type=int, default=10, help="训练轮数")
train_group.add_argument("--lr", type=float, default=0.001, help="学习率")
train_group.add_argument("--batch-size", type=int, default=32, help="批大小")

args = parser.parse_args()

帮助信息会自动分组显示。

四、子命令

4.1 add_subparsers

实现类似git commitgit push这样的子命令。

python
import argparse

parser = argparse.ArgumentParser(description="Agent工具")
subparsers = parser.add_subparsers(dest="command", help="子命令")

# train子命令
train_parser = subparsers.add_parser("train", help="训练模型")
train_parser.add_argument("--epochs", type=int, default=10, help="训练轮数")
train_parser.add_argument("--lr", type=float, default=0.001, help="学习率")

# predict子命令
predict_parser = subparsers.add_parser("predict", help="预测")
predict_parser.add_argument("--model", required=True, help="模型路径")
predict_parser.add_argument("--input", required=True, help="输入文件")

# evaluate子命令
eval_parser = subparsers.add_parser("evaluate", help="评估模型")
eval_parser.add_argument("--model", required=True, help="模型路径")
eval_parser.add_argument("--test-data", required=True, help="测试数据")

args = parser.parse_args()

if args.command == "train":
    print(f"训练 {args.epochs} 轮, lr={args.lr}")
elif args.command == "predict":
    print(f"使用 {args.model} 预测 {args.input}")
elif args.command == "evaluate":
    print(f"评估 {args.model}")
bash
python agent.py train --epochs 20 --lr 0.01
python agent.py predict --model model.pkl --input data.txt
python agent.py evaluate --model model.pkl --test-data test.txt
python agent.py --help

五、默认值与set_defaults

python
import argparse

parser = argparse.ArgumentParser()
parser.add_argument("--mode", default="train")
parser.set_defaults(mode="debug")  # 覆盖默认值

# 子命令也可以设置默认值
subparsers = parser.add_subparsers(dest="command")
train_parser = subparsers.add_parser("train")
train_parser.set_defaults(func="train_model")

六、格式化帮助信息

python
import argparse

# 保留描述格式
parser = argparse.ArgumentParser(
    description="这是一个\n多行描述\n会保留换行",
    formatter_class=argparse.RawDescriptionHelpFormatter
)

# 自动显示默认值
parser = argparse.ArgumentParser(
    formatter_class=argparse.ArgumentDefaultsHelpFormatter
)
parser.add_argument("--lr", type=float, default=0.001, help="学习率")
# 帮助信息会显示: 学习率 (default: 0.001)

七、实战示例

7.1 文件处理工具

python
import argparse

def main():
    parser = argparse.ArgumentParser(description="文件处理工具")
    parser.add_argument("input", help="输入文件")
    parser.add_argument("-o", "--output", help="输出文件(默认打印到终端)")
    parser.add_argument("-e", "--encoding", default="utf-8", help="文件编码")
    parser.add_argument("-v", "--verbose", action="store_true", help="详细输出")
    
    args = parser.parse_args()
    
    if args.verbose:
        print(f"读取文件: {args.input}")
    
    with open(args.input, encoding=args.encoding) as f:
        content = f.read()
    
    if args.output:
        with open(args.output, "w", encoding=args.encoding) as f:
            f.write(content)
        if args.verbose:
            print(f"写入文件: {args.output}")
    else:
        print(content)

if __name__ == "__main__":
    main()

7.2 CLI工具模板

python
import argparse
import sys

def train(args):
    print(f"训练: epochs={args.epochs}, lr={args.lr}")

def predict(args):
    print(f"预测: model={args.model}, input={args.input}")

def main():
    parser = argparse.ArgumentParser(description="ML工具")
    parser.add_argument("--verbose", "-v", action="store_true")
    subparsers = parser.add_subparsers(dest="command")
    
    # train
    p_train = subparsers.add_parser("train")
    p_train.add_argument("--epochs", type=int, default=10)
    p_train.add_argument("--lr", type=float, default=0.001)
    
    # predict
    p_predict = subparsers.add_parser("predict")
    p_predict.add_argument("--model", required=True)
    p_predict.add_argument("--input", required=True)
    
    args = parser.parse_args()
    
    if args.command == "train":
        train(args)
    elif args.command == "predict":
        predict(args)
    else:
        parser.print_help()
        sys.exit(1)

if __name__ == "__main__":
    main()

八、总结

argparse的核心:

组件用途
ArgumentParser创建参数解析器
add_argument()添加参数
parse_args()解析参数
add_subparsers()添加子命令

add_argument()常用参数:

参数用途
type参数类型
default默认值
required是否必选
choices可选值列表
action布尔/计数等特殊行为
nargs接受多个值
help帮助信息

argparsesys.argv好用太多了——自动处理类型转换、自动生成帮助文档、自动报错提示。写CLI工具必备。