- 人工智能
- 语音
- 音频
- 深度学习
- NLP
【免费下载链接】espnet
End-to-End Speech Processing Toolkit
导读
本文基于 ESPnet 仓库中 egs2/libriheavy_small/asr1/README.md 记录的官方 ASR 基线,系统讲解如何在 Libriheavy-Small 上复现 E-Branchformer 语音识别模型:从数据准备脚本、端到端训练配置(E-Branchformer 编码器 + Transformer 解码器)、CTC/注意力混合解码参数,到官方公布的 WER / CER / TER 评测结果。文章同时深入 e_branchformer_encoder.py 源码,说明双分支架构与分支融合机制的具体实现,帮助读者既能在实战中直接复现该基线,也能理解其背后原理。
Libriheavy-Small 与 E-Branchformer 基线概览
Libriheavy 是基于 LibriLight 语料构建的大规模英语语音识别数据集,ESPnet 在egs2/libriheavy_small/asr1目录下提供了使用 Libriheavysmall子集训练的官方 ASR 基线。该基线采用E-Branchformer编码器:
- 参数量:148.92 M
- ASR 训练配置:conf/tuning/train_asr_e_branchformer.yaml
- 预训练模型:由 ESPnet 团队发布并托管在 Hugging Face 的
espnet/libriheavy_small_ebranchformer模型仓库中(原始链接见 README 第 4 行),可用于直接推理或作为下游任务初始化权重。
训练环境的官方记录(见 README "Environments" 一节)为:
| 项目 | 版本 |
|---|---|
| 日期 | Fri Oct 18 10:37:57 WEST 2024 |
| Python | 3.10.14(conda-forge 打包,GCC 12.3.0) |
| ESPnet | espnet 202402 |
| PyTorch | 2.1.0 |
| Git hash | f6f011d328fb877b098321975280cadf8c64247a(commit 日期Tue Apr 9 01:44:27 2024 +0000) |
数据准备与训练流程
数据准备脚本
数据准备由 local/data.sh 完成,核心依赖两块数据:
- LibriLight 原始音频:需在 db.sh 中配置
LIBRILIGHT变量指向音频根目录(small、medium、large三个子目录需存在); - Libriheavy manifests:脚本会
git clone官方 Libriheavy 仓库,并通过其run.sh --stage 1 --stop-stage 2下载并解压各子集的 Kaldi 格式 manifest。
数据准备的四个阶段为:
- stage 1:检查 LibriLight 音频目录完整性,克隆 Libriheavy 仓库;
- stage 2:下载并解压 Libriheavy manifests(含
small/medium/large/test_clean/test_other/dev子集); - stage 3:将各子集的 Kaldi 格式数据目录复制到
data/下,并把wav.scp中的占位路径替换为实际的${LIBRILIGHT}路径,同时生成utt2spk(每个 utterance 视为独立说话人,awk '{print $1, $1;}')并执行utils/fix_data_dir.sh规范化; - stage 4:组合训练集,得到
train_large(large+medium+small)、train_medium(medium+small)与train_small(仅 small,直接复制)。
训练入口脚本
训练通过 run.sh 驱动,调用通用的./asr.sh管道,关键参数如下:
train_set="train_small" valid_set="dev" test_sets="dev test_clean test_other" asr_config=conf/train_asr.yaml inference_config=conf/decode_asr.yaml ./asr.sh \ --lang en \ --ngpu 1 \ --nbpe 5000 \ --max_wav_duration 30 \ --speed_perturb_factors "0.9 1.0 1.1" \ --asr_config "${asr_config}" \ --use_lm false \ --inference_config "${inference_config}" \ --train_set "${train_set}" \ --valid_set "${valid_set}" \ --test_sets "${test_sets}" \ --lm_train_text "data/${train_set}/text" \ --bpe_train_text "data/${train_set}/text" "$@"要点解读:
--nbpe 5000:使用 5000 个 BPE 子词单元,词表由训练集文本经 SentencePiece 训练得到;--speed_perturb_factors "0.9 1.0 1.1":对音频做 0.9 / 1.0 / 1.1 三档速度扰动实现数据增强(这也是实验目录名中sp后缀的由来);--max_wav_duration 30:过滤时长超过 30 秒的样本,控制训练 batch 的稳定性;--use_lm false:本基线不使用外部语言模型,解码仅依赖 ASR 模型本身;- 需要说明的是,虽然
run.sh默认指向 conf/train_asr.yaml,而 README 中记录的结果来自 conf/tuning/train_asr_e_branchformer.yaml(两个文件内容当前一致,均为 E-Branchformer 配置),复现官方结果时应以 README 指明的 tuning 配置为准。
训练配置深度解析
conf/tuning/train_asr_e_branchformer.yaml 是本次基线的核心配置,文件头部注释注明该配置在单张 A100 (80 GB)上训练得到。下面按模块逐一解读。
编码器:E-Branchformer
encoder: e_branchformer encoder_conf: output_size: 512 attention_heads: 8 attention_layer_type: rel_selfattn pos_enc_layer_type: rel_pos rel_pos_type: latest cgmlp_linear_units: 3072 cgmlp_conv_kernel: 31 use_linear_after_conv: false gate_activation: identity num_blocks: 17 dropout_rate: 0.1 positional_dropout_rate: 0.1 attention_dropout_rate: 0.1 input_layer: conv2d layer_drop_rate: 0.1 linear_units: 1024 positionwise_layer_type: linear macaron_ffn: true use_ffn: true merge_conv_kernel: 31对照 e_branchformer_encoder.py 中EBranchformerEncoder.__init__(L195-L227)的参数签名,各配置项含义如下:
output_size: 512:编码器模型维度(size),决定每个子层的输入输出维数;attention_heads: 8:多头注意力的头数;attention_layer_type: rel_selfattn:使用相对位置多头自注意力(RelPositionMultiHeadedAttention),要求pos_enc_layer_type: rel_pos配套(源码 L248-L250 有对应断言);pos_enc_layer_type: rel_pos/rel_pos_type: latest:使用最新的相对位置编码实现(RelPositionalEncoding)。源码 L231-L240 显示rel_pos_type仅有legacy(旧的 legacy 实现,会触发弃用警告)与latest两种取值,且latest模式下不允许与 legacy 注意力/位置编码混用;cgmlp_linear_units: 3072:Convolutional Gating MLP(CGMLP)分支中的前馈隐层维度;cgmlp_conv_kernel: 31:CGMLP 中深度可分离卷积的核大小,用于在 MLP 分支内建模局部上下文;use_linear_after_conv: false:卷积后是否再接一层线性投影(本项目关闭);gate_activation: identity:CGMLP 门控激活函数;num_blocks: 17:编码器堆叠 17 个 E-Branchformer 块;dropout_rate / positional_dropout_rate / attention_dropout_rate: 0.1:分别控制各子层、位置编码与注意力内部的 dropout;input_layer: conv2d:使用Conv2dSubsampling对原始帧(80 维 fbank)做下采样,将时间分辨率降低 4 倍;layer_drop_rate: 0.1:LayerDrop 概率,训练时随机跳过层以提升鲁棒性;linear_units: 1024:FFN 隐层维度;positionwise_layer_type: linear:FFN 采用标准线性结构;macaron_ffn: true/use_ffn: true:同时启用 macaron 风格 FFN 与常规 FFN。从 EBranchformerEncoderLayer 的实现可见,启用 macaron FFN 时其残差缩放系数ff_scale = 0.5(L91),而常规 FFN 的缩放系数保持 1.0;merge_conv_kernel: 31:分支融合模块中深度可分离卷积的核大小(见下文"双分支融合")。
解码器:Transformer
decoder: transformer decoder_conf: attention_heads: 8 linear_units: 2048 num_blocks: 6 dropout_rate: 0.1 positional_dropout_rate: 0.1 self_attention_dropout_rate: 0.1 src_attention_dropout_rate: 0.1 layer_drop_rate: 0.2解码器为 6 层标准 Transformer,8 注意力头、FFN 隐层 2048,并开启 LayerDrop(layer_drop_rate: 0.2)。相比编码器,解码器各注意力 dropout 均设为 0.1,与编码器保持一致。
模型级与训练超参数
model_conf: ctc_weight: 0.3 lsm_weight: 0.1 length_normalized_loss: false frontend_conf: n_fft: 512 hop_length: 160 use_amp: true unused_parameters: true num_workers: 4 batch_type: numel batch_bins: 35000000 accum_grad: 4 max_epoch: 80 patience: none init: none best_model_criterion: - - valid - acc - max keep_nbest_models: 10 nbest_averaging_interval: 10 optim: adam optim_conf: lr: 0.002 weight_decay: 0.000001 scheduler: warmuplr scheduler_conf: warmup_steps: 40000 specaug: specaug specaug_conf: apply_time_warp: true time_warp_window: 5 time_warp_mode: bicubic apply_freq_mask: true freq_mask_width_range: - 0 - 27 num_freq_mask: 2 apply_time_mask: true time_mask_width_ratio_range: - 0. - 0.05 num_time_mask: 10逐项解读:
ctc_weight: 0.3:混合 CTC/注意力训练中 CTC 损失的权重(1 - ctc_weight = 0.7 为注意力损失权重),与推理配置decode_asr.yaml中的ctc_weight: 0.3保持一致;lsm_weight: 0.1:标签平滑系数 0.1;length_normalized_loss: false:注意力损失不做序列长度归一化;frontend_conf:n_fft: 512、hop_length: 160,对应 16 kHz 采样率下 10 ms 帧移、约 32 ms 窗长的 fbank 提取设置;use_amp: true:启用自动混合精度训练(这是单卡 A100 能支撑大 batch 的关键之一);batch_type: numel / batch_bins: 35000000:按元素总数动态组 batch,将每个 batch 的元素总量控制在约 3500 万,避免显式按句子数组 batch 带来的长短不均;accum_grad: 4:梯度累积 4 步,等效增大有效 batch size;max_epoch: 80 / patience: none / init: none:最多训练 80 个 epoch,不启用早停与预训练初始化;best_model_criterion:以验证集acc(注意力识别准确率)最大化作为选优标准;keep_nbest_models: 10 / nbest_averaging_interval: 10:保留 10 个最佳模型并每 10 个模型间隔做一次权重平均(对应实验目录名中的asr_model_valid.acc.ave,即平均后模型);optim: adam / scheduler: warmuplr:Adam 优化器(lr=0.002,weight_decay=1e-6),配合 40000 步 warmup 的线性预热学习率调度;specaug:SpecAugment 数据增强——时间扭曲(窗口 5,bicubic 插值)、频域掩码(每样本最多 2 个掩码,宽度 0~27 个 bin)、时域掩码(每样本最多 10 个掩码,宽度为序列长度的 0%~5%)。
推理配置
解码阶段的设置见 conf/decode_asr.yaml:
beam_size: 60 ctc_weight: 0.3 lm_weight: 0.0beam_size: 60:beam search 的束宽为 60;ctc_weight: 0.3:解码时在注意力得分与 CTC 先验之间按 0.3/0.7 加权融合;lm_weight: 0.0:不加载外部语言模型,与训练阶段--use_lm false一致,说明最终 WER 完全由声学模型单独贡献。
官方评测结果
README 完整记录了训练后(含速度扰动增强,见实验名raw_en_bpe5000_sp)的评测结果。其中test_clean(2557 句)与test_other(2815 句)来自 LibriSpeech 风格的难易两档测试集,dev(5348 句)为 Libriheavy 开发集。
test_clean / test_other(平均后模型)
WER
| dataset | Snt | Wrd | Corr | Sub | Del | Ins | Err | S.Err |
|---|---|---|---|---|---|---|---|---|
| decode_asr_asr_model_valid.acc.ave/test_clean | 2557 | 102701 | 96.0 | 3.3 | 0.7 | 0.6 | 4.6 | 67.5 |
| decode_asr_asr_model_valid.acc.ave/test_other | 2815 | 111836 | 90.8 | 7.1 | 2.0 | 1.1 | 10.2 | 82.9 |
CER
| dataset | Snt | Wrd | Corr | Sub | Del | Ins | Err | S.Err |
|---|---|---|---|---|---|---|---|---|
| decode_asr_asr_model_valid.acc.ave/test_clean | 2557 | 533368 | 98.6 | 0.6 | 0.8 | 0.5 | 1.9 | 67.5 |
| decode_asr_asr_model_valid.acc.ave/test_other | 2815 | 581017 | 96.4 | 1.6 | 2.0 | 1.1 | 4.7 | 82.9 |
TER
| dataset | Snt | Wrd | Corr | Sub | Del | Ins | Err | S.Err |
|---|---|---|---|---|---|---|---|---|
| decode_asr_asr_model_valid.acc.ave/test_clean | 2557 | 127083 | 94.7 | 3.3 | 1.9 | 0.7 | 5.9 | 67.5 |
| decode_asr_asr_model_valid.acc.ave/test_other | 2815 | 144295 | 88.3 | 6.6 | 5.2 | 1.3 | 13.0 | 82.9 |
dev(开发集)
WER
| dataset | Snt | Wrd | Corr | Sub | Del | Ins | Err | S.Err |
|---|---|---|---|---|---|---|---|---|
| org/dev | 5348 | 218645 | 93.3 | 5.3 | 1.4 | 0.8 | 7.5 | 76.3 |
CER
| dataset | Snt | Wrd | Corr | Sub | Del | Ins | Err | S.Err |
|---|---|---|---|---|---|---|---|---|
| org/dev | 5348 | 1137810 | 97.5 | 1.1 | 1.4 | 0.8 | 3.3 | 76.3 |
TER
| dataset | Snt | Wrd | Corr | Sub | Del | Ins | Err | S.Err |
|---|---|---|---|---|---|---|---|---|
| org/dev | 5348 | 277457 | 91.4 | 5.0 | 3.7 | 1.0 | 9.6 | 76.3 |
指标含义说明:Snt为句子数,Wrd为词数,Corr/Sub/Del/Ins分别为正确率、替换、删除、插入错误,Err为最终词错误率,S.Err为句子错误率。整体来看,模型在 Libriheavy 长语音评测上表现出较高的字符级准确率(test_clean CER 1.9%),而句子级错误率(S.Err 约 67%~83%)较高,这与 Libriheavy 语料句子较长、句中错误容易被放大为整句错误的特点相符。
E-Branchformer 源码原理:双分支与融合
E-Branchformer 的核心思想是让每个编码器块内两条并行分支互补建模:一条用(相对位置)多头自注意力捕捉全局依赖,另一条用卷积门控 MLP(CGMLP)捕捉局部上下文。这在 e_branchformer_ctc_encoder.py 的EBranchformerEncoderLayer.forward(L116-L204)中有完整体现:
- Macaron FFN 前置:若启用
macaron_ffn,先经过缩放系数 0.5 的 macaron FFN 残差块; - 分支一(注意力):
x1 = norm_mha(x1)后送入相对位置多头注意力(L154-L165); - 分支二(CGMLP):
x2 = norm_mlp(x2)后送入ConvolutionalGatingMLP,卷积核大小由cgmlp_conv_kernel控制(L167-L176); - 双分支融合:将两条分支输出在特征维度拼接为
x_concat,然后执行x_tmp = mask_padded_frames(x_concat.transpose(1, 2), mask) x_tmp = self.depthwise_conv_fusion(x_tmp) # merge_conv_kernel 控制核大小 x = x + self.dropout(self.merge_proj(x_concat + x_tmp))即先做核大小为
merge_conv_kernel的深度可分离卷积做局部交互,再与原始拼接结果相加,经merge_proj线性投影回output_size维度,最后与残差相加(L178-L185)。注意mask_padded_frames确保融合卷积不会读取 padding 帧(L181 注释明确说明该设计意图); - 常规 FFN 与收尾:若启用
use_ffn,再经缩放系数 1.0 的常规 FFN 残差块,最终过norm_final。
本仓库中的 e_branchformer_encoder.py 提供标准实现(支持qk_norm、use_flash_attn、梯度检查点等扩展参数),而 e_branchformer_ctc_encoder.py 是 OWSM-CTC 系列使用的变体,额外支持交叉注意力与语言/任务前缀 token(详见文件头注释)。Libriheavy-Small 基线对应的是标准 E-Branchformer 路径。
小结与延伸
通过本文可以完整复现并理解 ESPnet 在 Libriheavy-Small 上的 E-Branchformer ASR 基线:
- 数据:LibriLight 音频 + Libriheavy Kaldi manifests,由 local/data.sh 完成准备与训练集组合;
- 训练:
./asr.sh配合 train_asr_e_branchformer.yaml,在单卡 A100 上完成 17 层 E-Branchformer + 6 层 Transformer 的端到端训练,并通过valid.acc选优与平均得到最终模型; - 解码:束宽 60、CTC 权重 0.3、无外部 LM,得到 test_clean WER 4.6% / test_other WER 10.2% 的官方基线结果;
- 原理:双分支(相对位置注意力 + CGMLP 卷积门控)经深度可分离卷积融合,兼顾全局与局部上下文建模,源码证据见 e_branchformer_encoder.py。
若需在更大规模数据上训练,可直接复用同一配置,仅将 run.sh 中的train_set改为train_medium或train_large(data.sh已内置相应组合逻辑),并相应调整batch_bins与max_epoch等资源相关参数。
- 人工智能
- 语音
- 音频
- 深度学习
- NLP
【免费下载链接】espnet
End-to-End Speech Processing Toolkit
相关推荐
ESPnet 的 Kathbath 多语种印度语 ASR 配方:E-Branchformer 训练、解码与评测全解析
ESPnet 的 Kathbath 多语种印度语 ASR 配方:E Branchformer 训练、解码与评测全解析 本篇技术指南基于 ESPnet 2 开源语
人工智能语音音频深度学习NLPESPnet 离散 Token ASR2 实战:Libriheavy small 上基于 WavLM + K-Means + E-Branchformer 的带大小写与标点识别
ESPnet 离散 Token ASR2 实战:Libriheavy small 上基于 WavLM + K Means + E Branchformer 的带
人工智能语音音频深度学习NLPESPnet Fisher CallHome Spanish 语音识别实战:E-Branchformer 与 Conformer 配置、训练与评测全解
ESPnet Fisher CallHome Spanish 语音识别实战:E Branchformer 与 Conformer 配置、训练与评测全解 本篇技术
人工智能语音音频深度学习NLP
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考