简介:本资源是专为VITS语音合成模型快速微调实践设计的开箱即用型样例数据包,面向语音合成初学者、AI开发者及需要定制化TTS能力的技术人员,解决从零配置环境、准备数据到启动训练的入门门槛问题。压缩包共983个文件,主体为979段高质量标注wav语音样本(覆盖多发音人与语境),辅以2个预训练模型权重(G_0.pth、D_0.pth)、1个微调专用配置文件(finetune_speaker.json)及1个音频采样说明文本(sampled_audio4ft.txt),整体大小587.21MB,目录结构简洁明确,便于直接加载训练。已有911人学习下载,资源提供完整微调链路支撑:无需自行收集数据或调试超参,可立即复现fine-tuning流程,验证模型在新音色/语种上的适配效果,并作为构建自有语音数据集的参考范本。
1. 先搞清楚这套流程到底在做什么
1.1 从一个真实需求说起
最近有不少朋友在问 VITS-Fast-Fine-Tuning 这套流程,尤其是一开始训练时就卡在“数据准备”这一步。很多人手头有几百条录音,也有明确的合成目标,但拿到项目后反而不知道怎么把素材喂进去。我一开始也是这个状态,所以想把这套流程从零到一完整拆一遍。
先说结论:VITS-Fast-Fine-Tuning 不是从零训练一个语音合成模型,而是在已有预训练模型的基础上,用你自己的语音数据做快速微调,让模型学会用你的音色去说话。所谓“样例数据”,本质上就是三类东西:预训练模型权重、配置文件、语音素材。这三者缺一不可,但很多教程只讲前两者,很少把语音素材的处理讲透。其实真正决定微调效果上限的,恰恰是语音素材的质量和格式。
这篇文章适合三类人:一是刚把代码 clone 下来、还没跑通数据准备的新手;二是已经尝试训练但 loss 不降、合成音质忽好忽坏的同学;三是想给自己的项目做一套标准化数据准备流程的开发者。我会把每一步、每一个关键参数背后为什么这么设置都讲清楚,方便你照着操作时心里有底。
1.2 VITS 和 Fast Fine-Tuning 的关系
VITS 本身是一个端到端文本转语音模型,它的特点是直接把文本输入映射成语音波形,不需要像传统 TTS 那样分多个模块。它内部用到了变分自编码器、Flow、Transformer 等结构,听起来复杂,但使用起来其实很简单:给它文本,它输出语音。
Fast Fine-Tuning 则是一套针对 VITS 的高效微调工程方案。它做了很多工程化优化,比如加载预训练模型后冻结部分层、调整学习率、支持低显存训练等。名字里的“Fast”主要体现在几方面:不需要从零训练,收敛速度快;数据量要求相对低,几十到几百条音频就能有可用效果;训练配置经过预先调优,不太需要反复试参数。
但需要注意,Fast Fine-Tuning 依然是微调,不是魔法。预训练模型本身提供了很强的“底层能力”,包括发音、韵律、多音字处理,微调只是让模型适应你的音色和说话习惯。如果你的数据质量不行,模型学习到的就是错误信息,后面合成出来的声音自然怪。
1.3 为什么样例数据这么重要
我在第一次跑这套流程时就犯过一个大错:只下载了预训练模型,随便找了几十条音频,没有整理文本对应关系,配置文件直接用默认值。结果训练了三个小时,loss 降了一些,但合成出来的声音完全不是目标音色,还夹杂大量破音和停顿。后来才发现,问题不在模型,而在数据准备环节。
样例数据的“准备”不只是把文件放到指定文件夹,它包含一系列格式转换、文本清洗、目录组织、参数调整动作。每一环节都会直接影响训练效果。比如音频采样率必须是 22050Hz,如果直接用微信语音或者从视频里扒出来的音频,可能采样率不对,模型读取时要么报错,要么质量受损。再比如文本标注文件里如果混有全角标点、数字、英文缩写,模型解析时也会出现对不齐的问题。
所以,这篇文章的核心就是围绕“如何把杂乱素材整理成模型能直接学习的样例数据”展开。我会按真实的操作顺序,从准备素材、准备预训练模型、修改配置文件,到最终跑通训练准备验证,一步步走一遍。整个过程不会太复杂,但细节很多,踩过一个坑就得返工,最好一次做对。
2. 训练前需要的素材清单与获取逻辑
2.1 核心素材:语音、文本、对应关系
先列出完整的素材清单,之后每项逐个说明:
| 素材类型 | 内容 | 格式要求 | 作用 |
|---|---|---|---|
| 语音素材 | 目标说话人的录音 | WAV,22050Hz,单声道,16bit | 提供音色和韵律特征 |
| 文本标注 | 与语音逐条对应的文本 | UTF-8 编码,无 BOM | 提供文字内容和发音依据 |
| 对应关系 | 音频文件名与文本的映射 | 固定分隔符文本文件 | 告诉模型哪段音频对应哪句话 |
| 预训练模型 | 基础模型权重文件 | .pt / .pth,路径正确 | 提供通用语言能力和发音基底 |
| 配置文件 | 模型参数、路径、训练参数 | .yaml / .json | 控制数据路径、训练策略和推理参数 |
语音素材是重中之重。不要混入不同音色的说话人,也不要在同一段音频里出现其他人说话。理想情况下,素材应当是目标说话人单独、安静环境下的朗读内容。如果只有带背景音乐或噪声音频,需要先做降噪、去混响处理,否则模型会把环境噪声当成说话人特征,合成时就会出现“底噪像呼吸声一样”的怪音。
文本标注要与音频内容完全一致。比如音频里说“今天天气很好”,标注文件里就不能写成“今天天气真好”。多音字、儿化音、轻声、数字、英文单词,都需要在预处理阶段统一规范。规则很简单:音频里怎么读,文本就怎么写。但这需要你反复听录音和文本比对,不能只靠自动识别脚本。
2.2 预训练模型:怎么选、怎么放
VITS-Fast-Fine-Tuning 一般会提供一个下载预训练模型的脚本,常见的预训练模型来源是项目维护者发布的公开权重。选型上主要看两个维度:一是语言,中文任务选中文预训练模型,英文任务选英文模型;二是采样率,预训练模型如果本身是 22050Hz 训练出来的,你的数据也要统一到 22050Hz。不要试图用 44100Hz 的模型微调 22050Hz 的数据,除非你改代码里所有与采样率相关的配置,否则大概率会出现音调异常。
模型放哪也很重要。一般项目里有一个 pretrained 目录,例如pretrained/{model_name}/。下载后要确认文件结构与项目 README 里预期的一致,包含模型权重文件和一个与配置文件对应的配置记录。有些预训练包可能包含了多个 checkpoint,不要在多个模型之间混用。
提示:如果下载到的预训练模型文件大小明显异常,比如只有几 KB,先检查下载过程是否被中断或者拿到的是错误文件。加载权重时报维度不匹配,大概率是模型文件与配置文件里的 hidden_size、num_layers 不一致。
另外,不建议在微调过程中继续保存全部中间 checkpoint,尤其是显存紧张的时候。训练脚本一般支持save_step参数,可以设置每多少步保存一次。为了省空间,可以只保存最后几个 checkpoint,因为微调中前期的权重不稳定,留太多没有意义。
2.3 配置文件:结构拆解与关键字段
配置文件是整个训练过程的“总指挥”。VITS-Fast-Fine-Tuning 的配置文件通常是.yaml格式,内容比较多,但真正需要改的核心字段并不多。下面这份是我实际项目里用到的简化示例,标注了每个字段的作用:
train: batch_size: 4 epochs: 300 learning_rate: 0.0002 fp16_run: true save_step: 1000 log_interval: 50 eval_interval: 1000 data: training_files: "filelists/train.txt" validation_files: "filelists/val.txt" text_cleaners: ["chinese_cleaners"] model: vocab_size: 178 hidden_channels: 192 filter_channels: 768 filter_channels_channel: 128 kernel_size: 3 p_dropout: 0.1 audio: sampling_rate: 22050 filter_length: 1024 hop_length: 256 win_length: 1024batch_size是根据显存调的,我不建议直接抄别人的 8 或 16,最好从 4 开始,训练时观察显存占用再逐步调大。learning_rate如果用默认 0.0002 效果不错,但如果你数据很少(比如只有几十条),可以降到 0.0001,避免过拟合。fp16_run开启后能显著降低显存占用,但需要算子支持,如果出现 NaN loss,再考虑关掉。
training_files和validation_files指向的是一个列表文件,里面每一行是“音频路径|文本”。这个文件格式非常关键,后面我会单独讲。vocab_size要和预训练模型一致,如果你改错了,加载权重时会报 embedding 维度错误。sampling_rate决定了音频读取时的重采样目标,所以音频素材必须统一到该值。
配置文件改完后,建议先运行一次数据校验脚本,确认所有路径都存在、文本能全部转换到音素、音频时长合理,再启动训练。
3. 样例数据的准备流程:从原始录音到可训练状态
3.1 音频处理:重采样、切片、去噪
这一节是整个训练准备中最繁琐、也最容易被忽视的部分。很多朋友拿到的录音可能是手机录的,也可能从视频里提取出来的,格式五花八门。但训练要求相对统一,建议一律转成 WAV、采样率 22050Hz、单声道、16bit 位深。这不仅是配置文件的要求,更是预训练模型内部声学特征的输入要求。
我平时用的是 FFmpeg,一条命令就能完成大部分转换:
ffmpeg -i input.mp3 -ar 22050 -ac 1 -sample_fmt s16 output.wav参数解释:-ar 22050是重采样到 22050Hz;-ac 1强制单声道;-sample_fmt s16保证 16bit。如果有多个文件,可以写一个简单的批处理脚本,把整个目录下的音频全部转一遍。
注意:重采样本身不会改善原始音频质量。如果你的原始音频是低码率、强压缩的,转成 WAV 后依旧是低质量,只是封装格式变了。所以最好在源头就保证录音环境安静、设备质量可靠。
接下来是切片。如果某条录音包含多句话,要用工具自动切片,也可以手动剪辑。我建议单条音频时长控制在 1 到 10 秒之间。太短的句子(比如一个字)信息量不足,会导致模型对单字发音过度拟合;太长的句子显存占用高,而且可能包含不自然停顿。普通正常语速下,一句 10 到 20 个字的朗读大约 3 到 5 秒,比较合适。
去噪方面,不要盲目使用强力降噪。过度降噪会让语音中高频细节丢失,合成出来的声音会发“闷”。如果录音底噪不明显,保留即可;如果底噪明显,可以用 Audacity 的降噪功能,先取一段纯噪声样本,再对整个文件进行降噪。降噪后要试听,确保人声没有明显失真。
3.2 文本标注与清洗:保证“音-字”对齐
文本标注的质量直接决定了训练时音素序列是否准确。VITS 最终使用的不是直接文本,而是先经过文本规范化,再转化为音素 ID。所以你的标注文本必须遵守以下规则:
- 使用中文简体,不要混入繁体;
- 标点使用半角逗号和句号,句号用英文句点
.也可,但同一文件里只保留一种; - 数字统一写成汉字,比如“123”写成“一百二十三”或“一二三”,具体看音频里怎么读;
- 英文单词如果不是为了调发音,尽量转写为中文读音一致的字;
- 不要保留 HTML 标签、表情符号、空格等多余字符。
做文本清洗时,我一般会写一个 Python 脚本做基础处理,但最终还是要人工逐条检查。下面是一个简单的清洗函数示例:
import re def clean_text(text): # 去掉多余空白 text = re.sub(r"\s+", "", text) # 统一标点:全角转半角 text = text.replace(",", ",").replace("。", ".") # 数字转汉字(简单示意,实际建议用 num2str 库) text = re.sub(r"\d", "数字占位", text) return text实际场景中,数字转汉字建议使用num2ch或cn2an这类库,处理量大的时候能省很多事。但要注意,“一百二十三”和“一二三”在 TTS 中对应不同的韵律,需要结合音频实际发音选择。
文本与音频的对应关系通过列表文件记录。VITS-Fast-Fine-Tuning 常见的文件是train.txt和val.txt,每行格式如下:
dataset/wavs/000001.wav|今天天气很好。 dataset/wavs/000002.wav|我们下午三点开会。注意分隔符是竖线|,不要用空格或逗号。路径是相对路径,相对于项目根目录。如果路径错了,训练时第一条数据就会报错。
3.3 文件目录组织与清单文件生成
数据组织没有唯一标准,但项目代码默认的路径通常如下:
dataset/ wavs/ 000001.wav 000002.wav filelists/ train.txt val.txt pretrained/ VITS-fast-fine-tuning/ ... configs/ config.yaml其中filelists目录不一定叫这个名字,有些项目叫filelists_22k,注意看代码里的路径定义。为了让后续训练不报错,建议严格参照项目 README 里的目录结构,不要自由发挥。
生成清单文件时要注意:训练集和验证集不能有重叠。否则验证集 loss 没有参考价值。我一般按 95:5 划分,数据少时留 3~5 条验证即可,不用刻意追求比例。验证集最好覆盖不同句长、不同语音风格,这样能观察到模型在不同情况下的表现。
划分完成后,写一个脚本统计音频时长分布,检查是否有过短或过长的音频。还可以写一个检查脚本,逐条确认音频文件和文本能对上。这一步可能看着“多余”,但能提前发现不少低级问题。
4. 实操:以一个小规模语料为例跑通准备流程
4.1 准备语音素材实录
我拿一个实际项目举例:小语料只有 50 条音频,来源是一段 40 分钟的录音,里面包含大量停顿和口水声。我的处理步骤是:
- 用工具自动切割出有效语音段,剔除沉默、重复、多人说话片段;
- 统一转码为 22050Hz 单声道 WAV;
- 用 Audacity 对每条音频做轻量降噪,目标是让底噪低于 -55dBFS;
- 手动逐条试听,删除有明显爆音、喷麦、翻页声的音频;
- 整理文件名,按
wavs/000001.wav到wavs/000050.wav顺序命名。
经过这轮处理,真正能用的音频只有 43 条。这很正常,宁缺毋滥。合成效果和有效音频数量、质量强相关,不要因为凑数量而保留低质量片段。
切片时我用的是一款开源切分工具,它能根据 VAD(语音活动检测)自动切分。如果你不想引入额外工具,也可以先用伪端点检测脚本切一遍,再人工调整。对于 50 条以下的小数据集,直接手动剪辑也不慢。
4.2 编写 metadata 和配置文件
素材整理好后,就要把每条音频对应的文本整理成列表文件。我建议先写一个临时文本文件,每条一行,记录文件名和听写文本,人工检查和录音校对,确认无误后,再批量编码为 UTF-8。
这里我踩过一个坑:Windows 的记事本保存文本文件时,默认可能是带 BOM 的 UTF-8,程序读取第一行时会多出不可见字符\ufeff,导致路径拼接失败。解决方式是用 VS Code 或 Python 显式以utf-8编码写入,并去掉 BOM。
with open("train.txt", "w", encoding="utf-8", newline="\n") as f: for line in lines: f.write(line + "\n")配置文件方面,我基于项目自带的configs/example.yaml改了几个关键字段:把training_files指向我的train.txt,validation_files指向val.txt,batch_size设为 2(因为我的显卡只有 6GB 显存),learning_rate保持默认。一开始我没改vocab_size,直接用预训练模型对应的值,这样加载权重时才不会报错。
提示:如果你手里的录音采样率和预训练模型不一致,不要只改配置文件里的
sampling_rate,最好把音频先统一重采样。因为音频特征提取层的参数与采样率是绑定的,强行只改配置文件会生成特征错位。
4.3 预训练权重放置与快速验证
下载好的预训练权重文件,我放在pretrained/finetune/下。不同版本的权重文件名可能不同,有些是G_0.pth,有些是model.pth。启动训练前,要确认代码读的是哪个文件。通常训练入口脚本里会有参数--model或--restore_path,指向具体权重路径。
放置好后,我会先跑一个“快速验证”脚本,一般项目会提供一个测试数据读取和模型前向的脚本。如果整个数据管线没有问题,这个脚本会打印出每一步加载成功的信息,并输出一个简短的音频样例。这一步虽然不影响训练,但能帮助我发现两个常见问题:一是文本转音素映射表缺失,二是音频特征与模型维度不匹配。
快速验证的输出音频通常很短,可以听一下。如果合成的是类似“嗯嗯啊啊”的语音,可能是模型没有正常加载预训练权重,随机初始化了。此时需要检查权重路径是否正确、配置文件里的vocab_size和权重文件是否一致。
5. 训练启动与常见问题排查
5.1 启动训练的关键命令与参数
准备完成后,启动训练的命令一般类似:
python train_ms.py -c configs/config.yaml -m pretrained/finetune-c指定配置文件路径,-m指定输出目录。有些版本还支持-r指定继续训练的 checkpoint,但微调场景一般不用。启动后,终端会在前几步打印出加载的数据条数、训练集长度、验证集长度等信息。如果这些信息不对,立刻停下来检查,不要等训练跑起来才发现。
训练过程中,我习惯每隔一段时间看一眼log_interval打印的 loss 值。VITS 的 loss 一般包含多个部分,包括重建损失、KL 散度等,整体趋势下降即正常。如果 loss 在几十步内快速降到很低,反而要警惕数据量太小导致过拟合;如果 loss 长时间不动,可能是学习率太低或数据有问题。
我的调度经验是:先用默认学习率跑 2000 步,如果 loss 震荡剧烈,就降一半学习率;如果下降太慢,可以适当调高。但每次只调整一个变量,不要同时改多个参数,否则很难定位问题。
5.2 本地训练常见报错与解决思路
训练准备阶段常见的错误,我按现象整理成了一张表:
| 报错现象 | 可能原因 | 解决方法 |
|---|---|---|
FileNotFoundError: wavs/000001.wav | 路径不对或清单文件里有空行 | 检查 train.txt 每一行路径,去掉空行 |
ValueError: text contains an invalid token | 文本里有不在字符表中的字符 | 清理特殊符号,统一标点和数字 |
RuntimeError: size mismatch for embedding | vocab_size与权重不匹配 | 使用预训练模型相同的vocab_size |
CUDA out of memory | batch_size太大或音频过长 | 调小batch_size,限制最大音频长度 |
| 训练时 loss 直接变 NaN | fp16 精度问题或数据异常 | 关闭fp16_run,检查文本是否为空 |
其中文本非法 token 这个问题最常见。VITS 使用一个预定义字符映射表,如果文本中出现了映射表之外的字符,比如 emoji、特殊箭头、数学符号,就会报错。解决思路很简单:统一清洗文本,只保留中文字符、常见英文大小写、半角标点和空白。写个正则把所有非目标字符删掉即可,但注意不要误删中文标点。
5.3 独家踩坑经验:小数据量微调的一些心得
最后分享几个我在实际操作中积累的经验,这些在文档里通常不会写。
第一,数据量特别少的时候,与其追求“准确复刻”,不如追求“稳定可听”。我试过 20 条数据微调,合成出来的声音能听出原音色,但每句话结尾的语调都变得很平,原因可能是语料中缺少丰富的句尾语调。如果你只能提供少量素材,建议尽量选择包含陈述、疑问、感叹不同语调的句子,让模型有更多韵律变化可以学。
第二,文本标注不要用纯自动语音识别生成,最好人工校正。自动识别在安静环境下准确率可能不错,但遇到人名、地名、专业术语容易出错。模型学到错误文本之后,合成时会出现“念错字”的问题,而且这种错误很难通过后期调参修复。
第三,训练到一半如果发现效果不佳,不要急着改配置文件重头训练。可以先加载最近一次 checkpoint,用少量测试文本合成,观察问题集中在发音、韵律还是音色上。如果是韵律问题,可以补充一些长句数据继续微调;如果是音色不像,可以检查数据里是否混入了其他人的声音。
第四,保存 checkpoint 时,注意区分G_(生成器)和D_(判别器)。推理时只需要加载生成器权重,千万别把判别器当成生成器用。我遇到过有朋友加载D_0.pth去推理,结果合成出来全是噪声,排查了很久才发现是加载错文件。
还有一个比较隐蔽的问题:VITS 模型的文本前端对“中文数字”的处理很敏感。音频里如果有多音字,比如“重庆”的“重”,文本是“重庆”本身没问题,但如果转换成拼音时选择了错误的声调,合成出来就会读错。所以如果发现某些字总是读错,可以在项目提供的 lexicon 字典里手动补充该字的发音,而不是去改训练数据。
这套流程跑通之后,后续再换新的说话人,只需要替换语音素材、文本标注和输出目录,重新生成清单文件,基本不需要动配置。我现在的做法是准备一个小的数据管理脚本,把音频处理、文本清洗、文件列表生成串在一起,每次换语料时直接跑一遍,省去了大量重复劳动。如果你刚开始接触 VITS-Fast-Fine-Tuning,建议先把这套准备流程固化下来,后面训练新数据集会轻松很多。
本文还有配套的精品资源,点击获取