- 人工智能
- 语音
- 音频
- NLP
- 媒体生成
【免费下载链接】PaddleSpeech
Easy-to-use Speech Toolkit including Self-Supervised Learning model, SOTA/Streaming ASR with punctuation, Streaming TTS with text frontend, Speaker Verification System, End-to-End Speech Translation and Keyword Spotting. Won NAACL2022 Best Demo Award.
导读:本文围绕 PaddleSpeech 中 U2(Unified Streaming and Non-streaming Two-pass End-to-end)ASR 模型的实验入口模块
paddlespeech.s2t.exps.u2.bin展开,逐一拆解train、test、test_wav、export、alignment五个子模块的源码实现、命令行参数与配置体系,并结合 examples/aishell/asr1 的真实脚本与 YAML 配置,说明从数据准备、多卡训练、模型平均、批量评测、单条音频推理到 JIT 模型导出的完整工程链路。读完本文,你将掌握 U2 模型在 PaddleSpeech 中"训练—验证—解码—导出—部署"的标准操作流程,并能直接照搬命令跑通自己的 ASR 实验。
一、paddlespeech.s2t.exps.u2.bin在项目中的定位
在 PaddleSpeech 的源码树中,paddlespeech/s2t/exps/u2/是 U2 模型的实验(experiment)目录,其下结构为:
paddlespeech/s2t/exps/u2/ ├── __init__.py ├── model.py # U2Trainer / U2Tester 核心实现 ├── trainer.py # 旧版 Trainer 实现(继承 Paddle 训练框架) └── bin/ ├── __init__.py ├── alignment.py # CTC 强制对齐入口 ├── export.py # 动转静导出 JIT 模型入口 ├── quant.py # 量化(PTQ)入口 ├── test.py # 批量评测入口 ├── test_wav.py # 单条音频推理入口 └── train.py # 训练入口Sphinx API 文档 docs/source/api/paddlespeech.s2t.exps.u2.bin.rst 正是为该bin包生成的 API 参考页。RST 中通过.. automodule:: paddlespeech.s2t.exps.u2.bin自动收集模块成员与继承关系,并通过 toctree 挂载了五个子模块:
paddlespeech.s2t.exps.u2.bin.alignment paddlespeech.s2t.exps.u2.bin.export paddlespeech.s2t.exps.u2.bin.test paddlespeech.s2t.exps.u2.bin.test_wav paddlespeech.s2t.exps.u2.bin.train也就是说,本文标题即对应文档主题:U2 模型实验程序的五个可执行入口。这些入口遵循同一套"命令行解析 → 配置文件装载 → Trainer/Tester 执行"的模板,代码量不大但信息密度高,是理解 PaddleSpeech ASR 工程化的最佳切入口。
U2 模型简介
U2 即Unified Streaming and Non-streaming Two-pass End-to-end Model for Speech Recognition(论文 arXiv:2012.05481),核心思想是让同一个模型同时支持流式与非流式解码:
- 训练阶段:采用 CTC 与 Attention 联合训练的混合架构,总损失为
loss = ctc_weight * loss_ctc + (1 - ctc_weight) * loss_att(见 paddlespeech/s2t/models/u2/u2.py); - 解码阶段:支持
attention、ctc_greedy_search、ctc_prefix_beam_search、attention_rescoring四种方式,其中attention_rescoring正是两遍式(two-pass)解码:第一遍用 CTC 前缀束搜索产生候选,第二遍用 Attention 解码器重打分。
U2 模型本体在paddlespeech/s2t/models/u2/下实现(U2Model、U2InferModel),而本文关注的exps/u2/bin则是围绕它搭建的训练/评测/导出外围。
二、统一的命令行入口与配置装载机制
所有bin/*.py脚本都遵循同一模式,以 train.py 为例:
if __name__ == "__main__": parser = default_argument_parser() args = parser.parse_args() print_arguments(args, globals()) config = config_from_args(args) print(config) maybe_dump_config(args.dump_path, config) pr = cProfile.Profile() pr.runcall(main, config, args) pr.dump_stats(os.path.join(args.output, 'train.profile'))三个关键点:
default_argument_parser():定义在 paddlespeech/s2t/training/cli.py,提供全实验共用的参数组:--conf:以文件形式装载配置;--config:训练配置文件(YAML)路径;--ngpu:并行进程数,0表示纯 CPU 训练;--seed:随机种子(None/0表示随机,非 0 会同时设置FLAGS_cudnn_deterministic=True);--output:checkpoint 保存目录;--checkpoint_path:加载的 checkpoint 前缀;--opts key value:以(KEY, VALUE)成对方式覆盖 YAML 中的任意字段,这是调参的快捷通道;--dump-config/--dump_path:将最终生效的配置落盘;- 测试组额外提供
--decode_cfg(解码配置)、--result_file(结果保存)、--audio_file(单音频推理); - 量化组提供
--audio_scp、--num_utts(校准样本数,默认 200)、--export_path(默认export.jit.quant)。
config_from_args(args):把--config指定的 YAML 与--opts覆盖项合并为最终配置对象。因此在 test.sh 中可以看到--opts decode.decoding_method ${type}这种运行时切换解码方式的用法。cProfile 性能剖析:训练/测试入口默认对主流程做性能剖析并输出
train.profile/test.profile,方便定位瓶颈。
从源码结构看,
quant.py虽然在仓库中实际存在,但 RST 文档的 toctree 只收录了 alignment/export/test/test_wav/train 五个子模块,未将 quant 纳入 API 文档页;本文按文档主题聚焦这五个入口,量化相关内容仅在导出章节顺带提及。
三、训练入口train.py:从 YAML 到多卡训练
train.py 的核心逻辑只有三行:
def main_sp(config, args): exp = Trainer(config, args) # Trainer = U2Trainer exp.setup() exp.run()其中Trainer从 paddlespeech/s2t/exps/u2/model.py 导入U2Trainer。U2Trainer继承自paddlespeech.s2t.training.trainer.Trainer,重写了四个关键方法:
3.1setup_dataloader:train/valid/test/align 四个数据集
def setup_dataloader(self): config = self.config.clone() self.use_streamdata = config.get("use_stream_data", False) if self.train: self.train_loader = DataLoaderFactory.get_dataloader('train', config, self.args) self.valid_loader = DataLoaderFactory.get_dataloader('valid', config, self.args) else: self.test_loader = DataLoaderFactory.get_dataloader('test', config, self.args) self.align_loader = DataLoaderFactory.get_dataloader('align', config, self.args)数据装载通过DataLoaderFactory工厂完成,数据源来自配置文件中的train_manifest/dev_manifest/test_manifest(Manifest 格式:每行一条 JSON,含utt、feat/audio_file、text等字段)。旧版 trainer.py 的实现则直接使用ManifestDataset+SpeechCollator+SortagradBatchSampler,其中sortagrad控制是否按音频时长排序(0 表示禁用、-1 表示所有 epoch 启用、其他值表示仅前 N 个 epoch 启用)。
3.2setup_model:模型构建、AMP 混合精度与优化器
model = U2Model.from_config(model_conf) self.use_amp = self.config.get("use_amp", True) self.amp_level = self.config.get("amp_level", "O1") if self.train and self.use_amp: self.scaler = paddle.amp.GradScaler(init_loss_scaling=self.config.get("scale_loss", 32768.0)) if self.amp_level == 'O2': model = paddle.amp.decorate(models=model, level=self.amp_level) else: self.scaler = None if self.parallel: model = paddle.DataParallel(model)值得注意的工程细节:
- AMP 默认开启(
use_amp默认True,amp_level默认O1),默认 loss 缩放系数 32768.0; - 优化器与学习率调度器均通过工厂创建:
OptimizerFactory.from_args(optim_type, ...)、LRSchedulerFactory.from_args(scheduler_type, scheduler_args)。从 model.py 可见调度器参数包含learning_rate、warmup_steps、gamma、d_model(取自encoder_conf.output_size),且noam优化器会启用beta1=0.9、beta2=0.98、epsilon=1e-9等默认值; input_dim/output_dim在训练时从train_loader.feat_dim/vocab_size动态获取,无需手工指定。
3.3train_batch:梯度累积与全局梯度裁剪
train_batch是训练的核心循环体(model.py):
loss /= train_conf.accum_grad ... if (batch_index + 1) % train_conf.accum_grad == 0: if train_conf.global_grad_clip != 0: if scaler: scaler.unscale_(self.optimizer) clip_grad_norm_(self.model.parameters(), train_conf.global_grad_clip) if scaler: scaler.step(self.optimizer) scaler.update() else: self.optimizer.step() self.optimizer.clear_grad() self.lr_scheduler.step() self.iteration += 1要点:
- 梯度累积:每
accum_grad个 batch 才做一次 optimizer step,等效扩大 batch size。期间通过model.no_sync(DDP 下)关闭梯度同步、只做本地累积,到累积边界再统一同步; - 全局梯度裁剪:
global_grad_clip非 0 时对全部参数执行clip_grad_norm_,且 AMP 下需先unscale_再裁剪(注释注明需要 paddlepaddle≥2.5); - 损失上报:
loss、att_loss、ctc_loss、batch_size、accum、step_cost均通过report()汇入观测流,并在do_train中汇总为batch_cost、samples、ips,samples/s等吞吐指标输出日志。
3.4do_train与valid:epoch 循环与多卡 loss 聚合
do_train以while self.epoch < self.config.n_epoch驱动,每个 epoch 结束后调用valid(),并在多卡场景下用dist.all_reduce聚合total_loss与num_seen_utts得到全局验证损失:
if dist.get_world_size() > 1: num_seen_utts = paddle.to_tensor(num_seen_utts) dist.all_reduce(num_seen_utts) total_loss = paddle.to_tensor(total_loss) dist.all_reduce(total_loss) cv_loss = total_loss / num_seen_utts每轮结束执行self.save(tag=self.epoch, infos={'val_loss': cv_loss})保存 checkpoint,并可通过 VisualDL 记录eval/cv_loss与eval/lr。
3.5 训练配置示例(AISHELL)
训练所需 YAML 配置可参考 examples/aishell/asr1/conf/conformer.yaml,核心段落包括:
# 网络结构 encoder: conformer encoder_conf: output_size: 256 # attention 维度 attention_heads: 4 linear_units: 2048 # 前馈网络隐层 num_blocks: 12 # 编码器块数 dropout_rate: 0.1 input_layer: conv2d # conv2d / conv2d6 / conv2d8 pos_enc_layer_type: 'rel_pos' selfattention_layer_type: 'rel_selfattn' decoder: transformer decoder_conf: attention_heads: 4 linear_units: 2048 num_blocks: 6 # 混合 CTC/Attention 训练 model_conf: ctc_weight: 0.3 # 混合权重,见 u2.py 中 loss 组合公式 lsm_weight: 0.1 # 标签平滑 length_normalized_loss: false # 数据 train_manifest: data/manifest.train dev_manifest: data/manifest.dev test_manifest: data/manifest.test vocab_filepath: data/lang_char/vocab.txt unit_type: 'char' feat_dim: 80 stride_ms: 10.0 window_ms: 25.0 sortagrad: 0 batch_size: 32 num_workers: 2 # 训练 n_epoch: 150 accum_grad: 8 global_grad_clip: 5.0 optim: adam optim_conf: lr: 0.002 weight_decay: 1.0e-6 scheduler: warmuplr scheduler_conf: warmup_steps: 25000 lr_decay: 1.0 log_interval: 100 checkpoint: kbest_n: 50 latest_n: 5配套的训练启动脚本 examples/aishell/asr1/local/train.sh 展示了单卡与多卡两种调用方式:
# 单卡/CPU(ngpu==0) python3 -u ${BIN_DIR}/train.py --ngpu 0 --seed 0 \ --config ${config_path} --output exp/${ckpt_name} # 多卡(使用 paddle.distributed.launch) python3 -m paddle.distributed.launch --gpus=${CUDA_VISIBLE_DEVICES} ${BIN_DIR}/train.py \ --ngpu ${ngpu} --seed ${seed} --config ${config_path} --output exp/${ckpt_name}脚本中还设置了FLAGS_allocator_strategy=naive_best_fit(避免显存不足时 GPU 训练挂起)以及可选的--ips多机参数。
四、批量评测入口test.py:四种解码方式与 CER/WER
test.py 导入的是U2Tester:
def main_sp(config, args): exp = Tester(config, args) with exp.eval(): exp.setup() exp.run_test()U2Tester继承自U2Trainer(model.py),额外持有TextFeaturizer(由unit_type、vocab_filepath、spm_model_prefix构建)用于 token 与文本互转。
4.1 核心方法compute_metrics
compute_metrics(model.py)完成"解码 + 指标计算"两件事:
error_rate_type = decode_config.error_rate_type # 'cer' 或 'wer' errors_func = error_rate.char_errors if error_rate_type == 'cer' else error_rate.word_errors reverse_weight = getattr(decode_config, 'reverse_weight', 0.0) result_transcripts, result_tokenids = self.model.decode( audio, audio_len, text_feature=self.text_feature, decoding_method=decode_config.decoding_method, beam_size=decode_config.beam_size, ctc_weight=decode_config.ctc_weight, decoding_chunk_size=decode_config.decoding_chunk_size, num_decoding_left_chunks=decode_config.num_decoding_left_chunks, simulate_streaming=decode_config.simulate_streaming, reverse_weight=reverse_weight)self.model.decode即U2Model.decode(见 paddlespeech/s2t/models/u2/u2.py),它按decoding_method分发到不同的解码器:
ctc_greedy_search:CTC 贪心解码;ctc_prefix_beam_search:CTC 前缀束搜索(通过CTCPrefixScorer实现),beam 大小由beam_size控制;attention:纯 Attention 自回归解码(teacher-forcing 式束搜索);attention_rescoring:两遍式——先用 CTC 前缀束搜索得到 N 个候选(代码中batch_size * beam_size的运行尺寸与logp.topk(beam_size)的扩展操作均服务于该流程),再用 Attention 解码器对候选重打分、取最优。
simulate_streaming为 True 且decoding_chunk_size > 0时,编码器改为按 chunk 增量前向(forward_chunk),用于模拟流式场景的精度评估。
4.2 结果输出与 RTF
test方法(model.py)将每条样本的utt / refs / hyps / hyps_tokenid以 JSONL 形式写入--result_file,同时统计:
- 实时率RTF = decode_time / (num_frames * stride_ms);
- 错误率
error_rate = errors_sum / len_refs(CER 或 WER 由配置决定); - 并额外生成
{result_file}.err元数据文件,包含epoch、step、rtf、error_rate、dataset_hour、process_hour、decode_method等实验信息,方便横向对比。
4.3 解码配置与评测脚本
解码配置单独放在一个 YAML 中,examples/aishell/asr1/conf/tuning/decode.yaml 完整内容如下:
beam_size: 10 decode_batch_size: 128 error_rate_type: cer decoding_method: attention # 'attention', 'ctc_greedy_search', 'ctc_prefix_beam_search', 'attention_rescoring' ctc_weight: 0.5 # ctc weight for attention rescoring decode mode. decoding_chunk_size: -1 # decoding chunk size. Defaults to -1. # <0: for decoding, use full chunk. # >0: for decoding, use fixed chunk size as set. # 0: used for training, it's prohibited here. num_decoding_left_chunks: -1 # number of left chunks for decoding. Defaults to -1. simulate_streaming: False # simulate streaming inference. Defaults to False.字段含义一览:
| 参数 | 默认值 | 说明 |
|---|---|---|
beam_size | 10 | 束搜索宽度 |
decode_batch_size | 128 | 解码 batch 大小;chunk 流式解码与束搜索模式需设为 1 |
error_rate_type | cer | cer或wer |
decoding_method | attention | 四种解码方式之一 |
ctc_weight | 0.5 | attention rescoring 时 CTC 得分权重 |
decoding_chunk_size | -1 | <0全量解码;>0固定 chunk;0仅训练使用、解码禁用 |
num_decoding_left_chunks | -1 | 流式解码允许的历史左侧 chunk 数 |
simulate_streaming | False | 是否模拟流式推理 |
配套评测脚本 examples/aishell/asr1/local/test.sh 展示了完整的四方式评测流程:
# 非 chunk 模型 for type in attention ctc_greedy_search; do python3 -u ${BIN_DIR}/test.py --ngpu ${ngpu} \ --config ${config_path} --decode_cfg ${decode_config_path} \ --result_file ${output_dir}/${type}.rsl --checkpoint_path ${ckpt_prefix} \ --opts decode.decoding_method ${type} \ --opts decode.decode_batch_size ${batch_size} python ${MAIN_ROOT}/utils/format_rsl.py --origin_hyp ${output_dir}/${type}.rsl --trans_hyp ${output_dir}/${type}.rsl.text python ${MAIN_ROOT}/utils/compute-wer.py --char=1 --v=1 \ data/manifest.test.text ${output_dir}/${type}.rsl.text > ${output_dir}/${type}.error done # 束搜索类解码(batch_size=1) for type in ctc_prefix_beam_search attention_rescoring; do batch_size=1 python3 -u ${BIN_DIR}/test.py ... --opts decode.decoding_method ${type} --opts decode.decode_batch_size ${batch_size} done注意脚本中的两条工程约束:
- 流式(chunk)模型(配置文件名匹配
chunk_*.yaml,如chunk_conformer.yaml)只能batch_size=1解码; ctc_prefix_beam_search与attention_rescoring同样要求batch_size=1;- 结果统一用 utils/compute-wer.py 或 sclite 计算 CER,其中
--char=1表示按字(字符级)计算。
五、单条音频推理入口test_wav.py:开箱即用的在线识别
test_wav.py 提供对单条 wav 文件的推理能力,直接面向在线使用场景。其流程与批量评测略有不同:它不走 DataLoader,而是实时做特征提取。
5.1 前向链路
U2Infer.run()(test_wav.py)的完整调用链为:
# 1. 读取音频(soundfile,强制 int16,取单声道) audio, sample_rate = soundfile.read(self.audio_file, dtype="int16", always_2d=True) audio = audio[:, 0] # 2. 在线特征提取(按 preprocess_config 定义的预处理管线) feat = self.preprocessing(audio, **self.preprocess_args) # 3. 模型解码 result_transcripts = self.model.decode(xs, ilen, text_feature=self.text_feature, ...) rsl = result_transcripts[0][0]其中preprocessing由Transformation(self.preprocess_conf)构建,preprocess_config指向配置中的conf/preprocess.yaml——这意味着测试时的 fbank 提取(含 CMVN 归一化)完全由该 YAML 驱动,与训练前处理保持严格一致。TextFeaturizer复用训练时的unit_type/vocab_filepath/spm_model_prefix构建词表。
5.2 模型加载方式
与批量评测从 checkpoint 目录自动恢复不同,test_wav.py直接加载权重文件:
params_path = self.args.checkpoint_path + ".pdparams" model_dict = paddle.load(params_path) self.model.set_state_dict(model_dict)即传入的--checkpoint_path指向xxx.pdparams权重前缀。
5.3 音频格式校验
check()函数对输入音频做了严格校验:文件必须存在、必须能被soundfile打开,且采样率必须为 16000Hz(assert (sample_rate == 16000))。这是使用该入口时必须满足的硬性前提。
启动方式对应 examples/aishell/asr1/local/test_wav.sh,其核心命令为:
python3 -u ${BIN_DIR}/test_wav.py \ --ngpu ${ngpu} \ --config ${config_path} \ --decode_cfg ${decode_config_path} \ --checkpoint_path ${ckpt_prefix} \ --audio_file ${audio_file} \ --opts decode.decoding_method ${type}六、模型导出入口export.py:动转静导出可部署的 JIT 模型
export.py 用于将训练好的 U2 模型导出为 Paddle 静态图 JIT 模型(供 C++ 推理引擎 / Paddle Inference 部署)。核心实现位于U2Tester.export()(model.py)。
6.1 导出模型与输入规格
load_inferspec()从U2InferModel.from_pretrained(...)构建推理模型,并返回(batch_size, feat_dim, model_size, num_left_chunks)四元组输入规格,其中batch_size固定为 1、num_left_chunks固定为 -1(表示非流式全量解码)。U2 的流式导出能力由U2InferModel的forward_feature/forward_encoder_chunk/ctc_activation/forward_attention_decoder四个可导出的子方法承载。
6.2 对四个子方法逐一做paddle.jit.to_static
export()为每个推理子方法声明InputSpec并转静态图:
# forward_feature:原始音频 → fbank 特征(int16 输入) infer_model.forward_feature = paddle.jit.to_static( infer_model.forward_feature, input_spec=[paddle.static.InputSpec(shape=[None], dtype='int16')]) # forward_encoder_chunk:增量编码器(含 att_cache / cnn_cache) infer_model.forward_encoder_chunk = paddle.jit.to_static( infer_model.forward_encoder_chunk, input_spec=[ paddle.static.InputSpec(shape=[batch_size, None, feat_dim], dtype='float32'), paddle.static.InputSpec(shape=[1], dtype='int32'), # offset num_left_chunks, # required_cache_size paddle.static.InputSpec(shape=[None, None, None, None], dtype='float32'), # att_cache paddle.static.InputSpec(shape=[None, None, None, None], dtype='float32')] # cnn_cache # ctc_activation:CTC 输出 infer_model.ctc_activation = paddle.jit.to_static( infer_model.ctc_activation, input_spec=[paddle.static.InputSpec(shape=[batch_size, None, model_size], dtype='float32')]) # forward_attention_decoder:Attention 解码(reverse_weight 固定 0.3) infer_model.forward_attention_decoder = paddle.jit.to_static( infer_model.forward_attention_decoder, input_spec=[ paddle.static.InputSpec(shape=[None, None], dtype='int64'), # hyps paddle.static.InputSpec(shape=[None], dtype='int64'), # hyps_lens paddle.static.InputSpec(shape=[batch_size, None, model_size], dtype='float32'), reverse_weight])6.3 保存与自校验
paddle.jit.save(infer_model, self.args.export_path, combine_params=True, skip_forward=True)导出完成后,代码会立即做一次动静态一致性自检:用相同的输入(paddle.full([1, 67, 80], 0.1)模拟特征、att_cache/cnn_cache初始化为零张量)分别跑动态图forward_encoder_chunk与加载后的静态图Layer.forward_encoder_chunk,再用np.testing.assert_allclose以atol=1e-5(编码器输出)与atol=1e-4(缓存张量)的精度断言两者一致。也就是说,导出脚本本身就内置了正确性回归测试,可放心用于后续部署。
导出命令封装在 examples/aishell/asr1/local/export.sh:
python3 -u ${BIN_DIR}/export.py \ --ngpu ${ngpu} \ --config ${config_path} \ --checkpoint_path ${ckpt_path_prefix} \ --export_path ${jit_model_export_path}导出产物即export.jit系列静态图文件,可衔接 PaddleSpeech 的 runtime C++ 推理引擎(runtime/engine/asr等)或 Paddle Inference 进行服务化部署。
七、CTC 对齐入口alignment.py:为下游数据标注提供对齐
alignment.py 是 U2 实验工具链中相对隐蔽但实用的一个入口,它调用U2Tester.align():
@paddle.no_grad() def align(self): ctc_utils.ctc_align(self.config, self.model, self.align_loader, self.config.decode.decode_batch_size, self.config.stride_ms, self.vocab_list, self.args.result_file)该功能使用训练好的模型对测试/对齐数据集执行CTC 强制对齐(force alignment),输出每个 token 在音频时间轴上的起止位置。这在语音数据标注、强制切分、韵律分析(如 TTS 前端训练数据的音素对齐)等场景中非常有用。align_loader在setup_dataloader中以keep_transcription_text=False(返回 token id)的方式构建(见 model.py)。
启动命令与评测类似:
python3 -u ${BIN_DIR}/alignment.py \ --ngpu ${ngpu} \ --config ${config_path} \ --decode_cfg ${decode_config_path} \ --result_file ${output_dir}/align.rsl \ --checkpoint_path ${ckpt_prefix}对应脚本为 examples/aishell/asr1/local/align.sh,在 run.sh 的 stage 4 被调用。
八、端到端串联:AISHELL 完整实验流程
将五个入口串起来,就是 examples/aishell/asr1/run.sh 的完整流水线:
# stage 0:数据准备 bash ./local/data.sh # stage 1:多卡训练(4 卡示例) CUDA_VISIBLE_DEVICES=${gpus} ./local/train.sh conf/conformer.yaml conformer # stage 2:平均最优模型(avg_num=30) avg.sh best exp/conformer/checkpoints 30 # stage 3:批量评测(attention / ctc_greedy_search / ctc_prefix_beam_search / attention_rescoring) CUDA_VISIBLE_DEVICES=0 ./local/test.sh conf/conformer.yaml conf/tuning/decode.yaml exp/conformer/checkpoints/avg_30 # stage 4:CTC 对齐 CUDA_VISIBLE_DEVICES=0 ./local/align.sh conf/conformer.yaml conf/tuning/decode.yaml exp/conformer/checkpoints/avg_30 # stage 5:单条音频识别 CUDA_VISIBLE_DEVICES=0 ./local/test_wav.sh conf/conformer.yaml conf/tuning/decode.yaml exp/conformer/checkpoints/avg_30 data/demo_01_03.wav # stage 51:导出 JIT 模型 CUDA_VISIBLE_DEVICES=0 ./local/export.sh conf/conformer.yaml exp/conformer/checkpoints/avg_30 exp/conformer/checkpoints/avg_30.jit阶段编排清晰地映射了本文五个入口的用途:train.py负责训练产出 checkpoint →utils/avg.sh平均多轮最优模型 →test.py批量评测并产出 CER/RTF →alignment.py产出强制对齐 →test_wav.py单条音频验证 →export.py导出静态图供部署。
九、实践要点与踩坑提示
结合源码与脚本,归纳使用paddlespeech.s2t.exps.u2.bin时的关键约束:
- 解码 batch 约束:
attention_rescoring、ctc_prefix_beam_search及所有 chunk 流式解码必须decode_batch_size=1,否则束搜索张量扩展逻辑(running_size = batch_size * beam_size)会出错或语义错误; - chunk 模型判定:
test.sh通过配置文件名是否匹配chunk_*.yaml自动进入流式模式,自定义配置文件请遵循该命名约定; - 解码参数边界:
decoding_chunk_size=0在解码阶段被禁止(源码assert decoding_chunk_size != 0),<0表示全量、>0表示固定 chunk; - 采样率硬性要求:
test_wav.py只接受 16kHz 单声道 wav(assert sample_rate == 16000),输入前需自行重采样; --opts覆盖机制:任何 YAML 字段都可通过--opts decode.decoding_method attention这种KEY VALUE成对形式在命令行覆盖,是调参与脚本化实验的关键手段;- AMP 与梯度裁剪:训练默认开启 AMP(O1),使用
global_grad_clip时需配合scaler.unscale_,并要求 paddlepaddle≥2.5; - checkpoint 结构:
--checkpoint_path传入的是权重前缀,训练产物含avg_30.pdparams、avg_30.pdopt等文件,评测与导出均基于此前缀。
十、总结
paddlespeech.s2t.exps.u2.bin是 PaddleSpeech 中 U2 模型实验的"总控面板":train.py驱动混合 CTC/Attention 训练(含 AMP、梯度累积、多卡聚合),test.py支撑四种解码方式的批量评测与 CER/RTF 统计,test_wav.py提供单音频在线推理,alignment.py产出 CTC 强制对齐,export.py完成动转静导出并内置一致性自检。五个入口共享default_argument_parser与config_from_args的统一框架,配合 examples/aishell/asr1 的脚本与 YAML 配置,即可完整复现"训练—评估—导出—部署"的 ASR 工程闭环。对希望深入理解 PaddleSpeech 实验框架或二次开发 U2 模型的开发者,本文涉及的文件(model.py、trainer.py、u2.py、cli.py)是直接可读、可验证的一手资料。
- 人工智能
- 语音
- 音频
- NLP
- 媒体生成
【免费下载链接】PaddleSpeech
Easy-to-use Speech Toolkit including Self-Supervised Learning model, SOTA/Streaming ASR with punctuation, Streaming TTS with text frontend, Speaker Verification System, End-to-End Speech Translation and Keyword Spotting. Won NAACL2022 Best Demo Award.
相关推荐
PaddleSpeech U2 统一流式/非流式 ASR 模型训练入口源码解析:paddlespeech.s2t.exps.u2.bin.train
PaddleSpeech U2 统一流式/非流式 ASR 模型训练入口源码解析:paddlespeech.s2t.exps.u2.bin.train 导读 pa
人工智能语音音频PaddleSpeech U2-ST 语音翻译模型源码解析:统一流式/非流式两遍端到端架构与多任务训练
PaddleSpeech U2 ST 语音翻译模型源码解析:统一流式/非流式两遍端到端架构与多任务训练 导读 本文围绕 PaddleSpeech 中语音翻译(S
人工智能语音音频NLP媒体生成PaddleSpeech u2_kaldi 实验模块解析:基于 Kaldi 工具链的 U2 端到端 ASR 训练、解码与对齐实战
PaddleSpeech u2_kaldi 实验模块解析:基于 Kaldi 工具链的 U2 端到端 ASR 训练、解码与对齐实战 本文以 PaddleSpeec
人工智能语音音频
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考