/egs
里一般存放执行的脚本,.sh
文件,讲了每一步要执行什么操作,而真正的算法程序部分,在/src
里的.cc
、.h
文件里。-
archive(.ark)、script(.scp) :是表格(table)一个‘表’就是一组有序的事物,前面是识别字符串(如句子的id),一个‘表’不是一个c++的对象,因为对应不同的需求(写入、迭代、随机读入)我们分别有c++对象来读入数据。Table有两种形式:“archive”和“script”文件。它们之间的差别在于:archive 包含实际的数据,而 script 文件则指出数据的具体位置。
.scp格式是text-only的格式,每行是个key(一般是句子的标识符(id))后接空格,接这个句子特征数据的路径 。
.ark格式可以是text或binary格式,(你可以写为text格式,命令行要加‘t’,binary是默认的格式)文件里面数据的格式是:key(如句子的id)空格后接数据。
-
.ark 和.scp 是 kaldi 中两种记录数 据的格式, .ark 是数据(二进制文件),scp 是记录对应 ark 的路径。 .ark 文件一般都是很大的(因为他们里面是真正的数据)
-
开头的ark:或scp:是要说明的格式,同名的 archive(.ark) 和 script(.scp) 文件代表的同一部分数据,注意,这 些命令行都有前缀”scp:” 或 “ark:”,kaldi 不会自己判断这到底是个 script 还是 archive 形式,这需要我们加前缀告诉 kaldi 这是什么格式的文件。对于 code 而言, 这两种格式对它来说都是一样的。
这两种格式都是‘表(table)’的概念。一个‘表’就是一组有序的事物,前面是 识别字符串(如句子的 id),一个‘表’不是一个 c++的对象,因为对应不同的需 求(写入、迭代、随机读入)我们分别有 c++对象来读入数据。
.scp 格式是 text-only 的格式,每行是个 key(一般是句子的标识符(id))后 接空格,接这个句子特征数据的路径 。
.ark 格式可以是 text 或 binary 格式,(你可以写为 text 格式,命令行要加‘t’, binary 是默认的格式)文件里面数据的格式是:key(如句子的 id)空格后接数据。
比如 raw_mfcc_dev.1.scp里的FNLP0_si1308 /Users/yelong/kaldi/egs/timit/s5/mfcc/raw_mfcc_test.3.ark:13意思是,打开存档(archive)文件,fseek()定位 到 13(字节),然后开始读数据。 -
rspecifier、wspecifiers用法 (P129)
常用的“o”(once)、“p”(permissive)、“s”(sorted)、“cs”(called-sorted)。
举例:"ark:o,s,cs:-"
"scp,p:data/my.scp"
1
2
从 Tabla 中读数据的程序需要一个“rspecifier”输入,该字符串指明了如何读 取索引数据;而写数据到 Table 中的程序需要一个“wspecifier”输入,该字符串 指示如何写数据。这两个字符串指出是否需要 scritpt 或 archive 文件,文件位置, 以及不同的选项。常用的“rspecifiers”有“ark:-”,表示从标准的输入中读取 archive 数据;而“scp:foo.scp”表示 script文件“foo.scp”会告诉我们从哪里去读取数据(因为scp文件只存了路径,)。 下面几点需要牢记:
- 冒号后面的部分被解释为“wxfilename”或“rxfilename”(与 Non-table I/O 中一样),这意味着管道和标准的输入/输出均可支持。
- 一个 Table 通常只包含一种类型的对象(例如浮点型矩阵)
- 你可以查看“rspecifiers”和“wspecifiers”中的选项,主要有:
- 在“rspecifiers”中,“ark,s,cs:-”表示当我们读数据时,我们希望keys是有序的(s),以及我们会按顺序访问数据(cs),若这些条件不满足时,程序会崩溃。这些保证了Kaldi中高效的的随机访问,而不占用大量的内存。
- 对于规模较少并且不太方便进行排序列的数据(例如:说话人自适应 应变换矩阵),若省略掉 s, cs 参数,几乎没有损害。
- 当Kaldi程序有多个“rspecifiers”输入时,程序会轮流访问相应的对象;其中第一个使用顺序访问,而后面的采用随机访问,因此,第一个“rspecifier”不需要“s, cs”选项。
- 在访问script文件时,例如“p:foo.scp”,其中“p”意味着当我们 需要的文件不存在时,程序不会崩溃(对于 archive,当期望的文 件被破坏或被截断时,“p”也地阻止程序崩溃)。
- 写数据时,选项“t”表示文本模式,例如:“ark,t:-”。“-binary” 命令行选项对 archives 无效。
- Script 文件每一行的格式为:“
-
L.fst 文件是编译后的 FST 格式的词典(lexicon)
训练好的模型,一般是.mdl后缀,里面用命令打开,是很详细的过程,第一部分是做什么的,然后一堆参数,第二部分是做什么的,一堆参数。模型都是一堆参数。输入特征,输出声学模型、语言模型。
在shell里gcc,kaldi里的/src文件里的很多没有后缀的可执行文件,都是可以直接运行编译的,只要把path加进去,然后变量名添加一下,几乎不用改动很多,就能运行。重点就是要理解c++的算法,经常需要单步调试。shell里也是可以单步调试的。
monophone 单音素训练, tri1 三因素训练, trib2 进行 lda_mllt 特征变换,trib3 进行 sat 自然语言适应
tri1 下,final.mdl,这个就是有用的东西,学出来的模型。
graph_word 下,找到 words.txt,和 HCLG.fst,一个是字典,一个是有限状态机
HCLG.fst:解码图(有限状态机),利用先前创建的语言模型和上步训练的声学模型构建HCLG解码图。
步骤是固定的:mono,tri1,tri2,tri3.不能因为tri1训练解码效果不好,就跳过它,因为后面都是基于前面
-
mono:train_mono.sh 用来训练单音子隐马尔科夫模型,一共进行40次迭代,每两次迭代进行一次对齐操作
tri1:三音素。train_deltas.sh 用来训练与上下文相关的三音子模型
tri2:tri1上加上lda + mllt。用来进行线性判别分析和最大似然线性转换
tri3:再加上说话人自适应Speaker Adapted Training (SAT),。用来训练发音人自适应,基于特征空间最大似然线性回归
quick:用来在现有特征上训练模型。
对于当前模型中在树构建之后的每个状态,它基于树统计中的计数的重叠判断的相似性来选择旧模型中最接近的状态。然后评价模型的效果,需要识别出一批数据,然后计算word error rate (wer)词错误率,kaldi里面有个 local/score.sh
./run.sh 之前,要先. ./path.sh一下
egs/sre08、sre10、sre16、lre、aishell/v1:说话人识别
-
tri*_ali:align对齐
*.txt:是OpenFst格式里的符号表symbol tables,比如words.txt。
map:映射的意思。Use Vector Quantization (VQ) to map each speech feature to one symbol (out of typically around 256).
使用代理关键词以处理表外词(OOV)
steps/make_mfcc.sh 特征提取
steps/compute_cmvn_stats.sh 计算每条wav文件的均值方差
utils/mkgraph.sh (HCLG)(建立完全的识别网络,输出是一个有限状态转换器。每次训练出一种新的种类模型后都需要执行该脚本生成识别网络。)
steps/align_si.sh 运行指定模型对指定数据进行对齐,一般在新的模型开始训练前调用,上一个版本训练的模型作为输入
steps/train_deltas.sh triphon 训练三因素绑定
steps/decode.sh 解码数据,使用命令gmm-latgen-faster, gmm-decode-faster, compute-wer
.si后缀:speaker independent ,比如decode_test_phone.si
decode_test_phone_it3:_it迭代
-
LSTM + CTC
该算法也是开源的,在
eesen
(基于Kaldi的LSTM语音识别工具)里。kaldi里面的算法都是:
DNN +HMM hybrid 模型
-
fst:加权有限状态
kaldi解码过程
kaldi识别解码一段语音的过程是:首先提取特征,然后过声学模型AM,然后过解码网络HCLG.fst,最后输出识别结果。
HCLG是解码时的重要组成部分。HCLG.fst是由4个fst经过一系列算法(组合、确定化和最小化等)组合而成的。
4个fst分别是H.fst、C.fst、L.fst和G.fst,分别是HMM模型、上下文环境、词典和语言模型对应的fst。fst可视化的两个基本命令
stprint和fstdraw是可视化用到的两个基本命令
fstprint用于打印fst,可以将二进制的fst以文件形式打印出来。Fstprint的基本用法如下
fstprint [–isymbols=xxxx –osymbols=xxxx ] FST
参数—isymbols和—osymbols分别表示输入符号表和输出符号表,这两个参数可以省略。
fstdraw用于画fst图,其使用方式跟fstprint类似。Fstdraw得到的结果是dot文件,通过dot命令转为ps格式,然后可以由ps2pdf命令转为pdf文档。stdraw使用示例
fstdraw [--isymbols=phones.txt --osymbols=words.txt] L.fst | dot –Tps | ps2pdf – L.pdf
1
.mdl 文件 (P117)
copy-tree --binary=false exp/mono/tree - | less
1
转移状态 (P119)
训练前的初始状态show-transitions data/lang/phones.txt exp/mono/0.mdl
1
为了增加可读性,输入:show-alignments data/lang/phones.txt exp/mono/40.mdl exp/mono/40.occs | less
1
(.occs 文件是指 occupation counts)文件名表示
文件名可以被“-”替代(“-”表示标准输入输出); 也可以被字符串(如“|gzip -c >foo.gz” or “gunzip -c foo.gz|”)来替代(rspecifier、wspecifiers)。命令用法
1.
timit=/Users/yelong/kaldi/egs/timit/data
local/timit_data_prep.sh $timit || exit 1这里.sh后面怎么接了一个路径呢,原来这个路径参数是作为传进.sh的参数传进去(就是.sh里的$1)。
2.
一般执行了exit 1说明有问题,前面语句有问题才会执行这句;而exit 0说明没问题,类似return 0。 -
spk2gender 包含说话人的性别信息
- spk2utt 包含说话人编号和说话人的语音编号的信息
- text 包含语音和语音编号之间的关系
- utt2spk 语音编号和说话人编号之间的关系
- wav.scp 包含了原始语音的路径信息等 -
train_mono.sh 用来训练单音子隐马尔科夫模型,一共进行40次迭代,每两次迭代进行一次对齐操作
train_deltas.sh 用来训练与上下文相关的三音子模型
train_lda_mllt.sh 用来进行线性判别分析和最大似然线性转换
train_sat.sh 用来训练发音人自适应,基于特征空间最大似然线性回归
nnet3/run_dnn.sh 用nnet3来训练DNN,包括xent和MPE
用chain训练DNN -
teps/make_mfcc.sh 特征提取
steps/compute_cmvn_stats.sh 计算每条wav文件的均值方差
steps/train_mono.sh monophon训练
utils/mkgraph.sh (HCLG)(建立完全的识别网络,输出是一个有限状态转换器。每次训练出一种新的种类模型后都需要执行该脚本生成识别网络。)
steps/align_si.sh 运行指定模型对指定数据进行对齐,一般在新的模型开始训练前调用,上一个版本训练的模型作为输入
steps/train_deltas.sh triphon 训练三因素绑定
steps/decode.sh 解码数据,使用命令gmm-latgen-faster, gmm-decode-faster, compute-wer
-
kaldi中常用的linux命令:https://blog.csdn.net/eqiang8848/article/details/81781230
-
-
-
-
-
-
-
-
-
-
若path.sh是常规文件就运行之:-f 判断path.sh是否常规文件,另,常见文件判断命令如下:
-e filename 如果 filename存在,则为真
-d filename 如果 filename为目录,则为真
-f filename 如果 filename为常规文件,则为真
-L filename 如果 filename为符号链接,则为真
-r filename 如果 filename可读,则为真
-w filename 如果 filename可写,则为真
-x filename 如果 filename可执行,则为真
-s filename 如果文件长度不为0,则为真
-h filename 如果文件是软链接,则为真
filename1 -nt filename2 如果 filename1比 filename2新,则为真。
filename1 -ot filename2 如果 filename1比 filename2旧,则为真。
-eq 等于
-ne 不等于
-gt 大于
-ge 大于等于
-lt 小于
-le 小于等于
!非 -
compute_cmvn_stats.sh 是为了计算提取特征的CMVN,即为倒谱方差均值归一化!
-
参考:
1.https://blog.csdn.net/eqiang8848/article/details/81781370
2.https://blog.csdn.net/eqiang8848/article/details/81543599
3.https://blog.csdn.net/rooki_men/article/details/52163996