kaldi基於GMM的單音素模型 訓練部分

[TOC]html

轉載註明出處。算法

1. gmm-init-mono 模型初始化

  • gmm-init-mono --train-feats=ark:feats.ark topo 39 0.mdl tree
  • 0.mdl 中使用初始化的狀態轉換機率,其中 pdf模型共享參數。
  • tree中的樹爲提出兩個問題,第一個問題爲各個音素是什麼,第二個問題爲狀態爲第幾個。

實例:bash

  • 將特徵進行均值方差歸一化後抽取一階差分和二階差分:
/home/speech.AI/kaldi/src/featbin/apply-cmvn scp:cmvn.scp scp:copy-feats.scp ark:- | /home/speech.AI/kaldi/src/featbin/add-deltas ark:- ark:delta.ark
  • 利用提取的39維特徵進行進行模型初始化:
gmm-init-mono --train-feats=ark:delta.ark topo 39 0.mdl tree

2. compile-train-graghs 訓練圖初始化

  • 使用compile-train-graghs生成訓練用的FST,是每一個句子構造一個FST網絡:
Usage: compile-train-graphs [options] <tree-in> <model-in> <lexicon-fst-in> <transcriptions-rspecifier> <graphs-wspecifier> 
e.g.:  compile-train-graphs tree 1.mdl lex.fst ark:train.tra ark:graphs.fsts

其中的ark:train.tra通常經過ark:sym2int.pl -f 2- words.txt text|利用詞典將文本信息轉化爲對應的音素序號。網絡

下面是個人路徑下的測試命令:app

/home/speech.AI/kaldi/src/bin/compile-train-graphs 0.tree 0.mdl ../data/lang/L.fst 'ark:/home/speech.AI/kaldi/egs/wsj/s5/utils/sym2int.pl -f 2- words.txt text|' ark:graphs.fsts

3. align-equal-compiled 特徵文件均勻分割

  • 使用align-equal-compiled根據咱們獲得的訓練用的fst對特徵文件進行均勻分割。
  • 須要留意,切割的文件中間都摻雜着SIL單詞,可是標註中沒有體現,我還不知道爲什麼,切對齊文件每一個狀態的幀數也不相同。
Usage: align-equal-compiled <graphs-rspecifier> <features-rspecifier> <alignments-wspecifier>
e.g.:  align-equal-compiled ark:graphs.fsts ark:delta.ark ark:equal.ali
  • 對文件的每一幀進行均勻標準,具體算法不瞭解:
[2 1 1 1 1 1 1 1 1 6 5 5 5 5 5 5 5 5 11 10 10 10 10 10 10 10 10 13 15 15 15 15 15 15 15 15 8 5 5 5 5 5 5 5 5 18 17 17 17 17 17 17 17 17 26 25 25 25 25 25 25 25 25 28 27 27 27 27 27 27 27 27 30 29 29 29 29 29 29 29 29 4 1 1 1 1 1 1 1 1 14 15 15 15 15 15 15 15 15 12 10 10 10 10 10 10 10 10 18 17 17 17 17 17 17 17 17 26 25 25 25 25 25 25 25 25 28 27 27 27 27 27 27 27 27 30 29 29 29 29 29 29 29 29 2 1 1 1 1 1 1 1 1 6 5 5 5 5 5 5 5 5 11 10 10 10 10 10 10 10 10 13 15 15 15 15 15 15 15 15 8 5 5 5 5 5 5 5 5 18 17 17 17 17 17 17 17 17 26 25 25 25 25 25 25 25 25 28 27 27 27 27 27 27 27 27 30 29 29 29 29 29 29 29 29 3 1 1 1 1 1 1 1 1 9 10 10 10 10 10 10 10 10 7 5 5 5 5 5 5 5 5 14 15 15 15 15 15 15 15 15 9 10 10 10 10 10 10 10 10 7 5 5 5 5 5 5 5 5 13 15 15 15 15 15 15 15 15 7 5 5 5 5 5 5 5 5 14 15 15 15 15 15 15 15 15 12 10 10 10 10 10 10 10 10 18 17 17 17 17 17 17 17 17 26 25 25 25 25 25 25 25 25 28 27 27 27 27 27 27 27 27 30 29 29 29 29 29 29 29 29 4 1 1 1 1 1 1 1 13 15 15 15 15 15 15 15 15 7 5 5 5 5 5 5 5 16 15 15 15 15 15 15 15 18 17 17 17 17 17 17 17 20 19 19 19 19 19 19 19 22 21 21 21 21 21 21 21 24 23 23 23 23 23 23 23 3 1 1 1 1 1 1 1 11 10 10 10 10 10 10 10 13 15 15 15 15 15 15 15 6 5 5 5 5 5 5 5 11 10 10 10 10 10 10 10 14 15 15 15 15 15 15 15 9 10 10 10 10 10 10 10 8 5 5 5 5 5 5 5 18 17 17 17 17 17 17 17 20 19 19 19 19 19 19 19 22 21 21 21 21 21 21 21 24 23 23 23 23 23 23 23 3 1 1 1 1 1 1 1 11 10 10 10 10 10 10 10 16 15 15 15 15 15 15 15 18 17 17 17 17 17 17 17 20 19 19 19 19 19 19 19 22 21 21 21 21 21 21 21 24 23 23 23 23 23 23 23 20 19 19 19 19 19 19 19 22 21 21 21 21 21 21 21 24 23 23 23 23 23 22 23 2 1 1 1 1 1 1 1 7 5 5 5 5 5 5 5 14 15 15 15 15 15 15 15 12 10 10 10 10 10 10 10 18 17 17 17 17 17 17 17];

均勻分割後的每一幀trans-id的標註,不知道爲什麼每一個音素的時間並不相同,也不知道緣由。 且每一個單詞中間都出現了未被標註的靜音音素。 YESNO爲例對齊後每一幀狀態轉移id 實例:ide

home/speech.AI/kaldi/src/bin/align-equal-compiled ark:graphs.fsts ark:delta.ark ark:equal.ali

4. gmm-acc-stats-ali 累積模型重估所需數據

Usage: gmm-acc-stats-ali [options] <model-in> <feature-rspecifier> <alignments-rspecifier> <stats-out>
e.g.:  gmm-acc-stats-ali 1.mdl scp:train.scp ark:1.ali 1.acc
  • 對於每一幀的特徵和其對齊(transition-id):oop

    • 對於轉移模型(TM),累積tid出現的次數;
    • 對於AM,由tid獲得pdf-id,也就是找到對應該pdf-id的DiagGmm對象,更新與該DiagGmm對象相關的AccumDiagGmm的參數,也就是計算獲得三個GMM參數更新公式的分子部分(包括每一混合份量的後驗(occupancy_中保存$∑nj=1γ^jk$)、每一份量的後驗乘以當前幀的特徵(mean_accumulator_中保存$∑nj=1γ^jkyj$,$MxD$維)、每一份量的後驗乘以 當前幀的特徵每一維的平方(variance_accumulator_中保存$∑nj=1γ^jky2j$,$MxD$維))
  • 處理完全部數據後,將TM和AM的累積量寫到一個文件中:x.JOB.acc中post

實例:測試

/home/speech.AI/kaldi/src/gmmbin/gmm-acc-stats-ali 0.mdl ark:delta.ark ark:equal.ali 0.acc

5. gmm-sum-accs 並行數據合併

  • gmm-acc-stats-ali生成的累計量分散在JOB個文件中,該程序將分散的對應同一trans-id、pdf-id的累計量合併在一塊兒 若是不是多個線程就沒必要進行合併。
Usage: gmm-sum-accs [options] <stats-out> <stats-in1> <stats-in2> ...
E.g.:  gmm-sum-accs 1.acc 1.1.acc 1.2.acc

6. gmm-est 聲音模型參數重估

  • 做用:Do Maximum Likelihood re-estimation of GMM-based acoustic model.調用gmm-est對0.mdl進行從新估計,該程序對基於GMM的聲學模型進行最大似然從新估計,生成exp/mono/1.mdl
Usage: gmm-est [options] <model-in> <stats-in> <model-out>
e.g.:  gmm-est 1.mdl 1.acc 2.mdl

實例:this

/home/speech.AI/kaldi/src/gmmbin/gmm-est 0.mdl 0.acc 1.mdl

7. gmm-boost-silence 模型平滑處理

  • 做用:修改基於GMM的模型以(經過某個因素)提高與指定電話相關的全部機率(能夠是全部靜音電話,或者僅用於可選靜音)。 注意:這是經過修改GMM權重來完成的。 若是沉默模型與其餘模型共享GMM,則它將修改可能對應於靜音的全部模型的GMM權重
  • Modify GMM-based model to boost (by a certain factor) all probabilities associated with the specified phones (could be all silence phones, or just the ones used for optional silence). Note: this is done by modifying the GMM weights. If the silence model shares a GMM with other models, then it will modify the GMM weights for all models that may correspond to silence.
Usage:  gmm-boost-silence [options] <silence-phones-list> <model-in> <model-out>
e.g.: gmm-boost-silence --boost=1.5 1:2:3 1.mdl 1_boostsil.mdl

實例:

/home/speech.AI/kaldi/src/gmmbin/gmm-boost-silence --boost=1.0 1 1.mdl 1_new.mdl

8. gmm-align-compiled 特徵從新對齊

  • 使用新的模型和原來的訓練狀態圖對原來的特徵文件進行從新對齊。
Usage: gmm-align-compiled [options] <model-in> <graphs-rspecifier> <feature-rspecifier> <alignments-wspecifier> [scores-wspecifier]
e.g.:  gmm-align-compiled 1.mdl ark:graphs.fsts scp:train.scp ark:1.ali
  • 或者從新編譯新的訓練狀態圖而後對齊:
or: compile-train-graphs tree 1.mdl lex.fst 'ark:sym2int.pl -f 2- words.txt text|' ark:- | gmm-align-compiled 1.mdl ark:- scp:train.scp t, ark:1.ali

實例:

  • 首先從新生成訓練圖:
/home/speech.AI/kaldi/src/bin/compile-train-graphs 0.tree 1.mdl ../data/lang/L.fst 'ark:/home/speech.AI/kaldi/egs/wsj/s5/utils/sym2int.pl -f 2- words.txt text|' ark:graphs_new.fsts
  • 而後使用新的解碼圖進行對齊:
/home/speech.AI/kaldi/src/gmmbin/gmm-align-compiled 1.mdl ark:graphs_new.fsts ark:delta.ark ark,t:ali1.txt

而後就能夠得到新的對齊標註:

3 1 12 10 10 10 18 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 26 25 25 25 28 27 27 27 27 27 27 27 30 29 29 29 29 29 29 29 29 29 29 29 29 29 29 2 7 5 5 5 13 15 15 15 15 15 7 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 14 15 15 15 15 15 9 10 7 5 5 5 13 15 15 15 15 15 15 8 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 18 17 17 17 17 17 17 17 17 17 26 25 25 25 25 28 27 27 27 27 27 27 27 27 27 27 27 30 29 29 29 29 29 29 29 29 29 29 2 1 1 1 1 1 6 5 9 10 10 10 10 10 8 5 5 5 5 5 5 5 5 5 5 18 17 17 17 17 17 26 25 25 25 28 27 27 27 27 27 27 27 27 27 27 27 27 27 30 29 29 29 29 29 29 29 29 29 29 29 2 8 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 18 17 17 17 17 17 17 17 17 26 25 25 25 25 25 25 25 25 25 28 27 27 27 27 27 27 27 30 29 29 29 29 29 29 29 29 29 2 1 1 1 1 1 1 1 1 1 1 1 1 8 5 5 5 5 5 18 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 20 19 19 19 19 19 19 19 19 19 19 22 21 21 21 21 21 21 21 21 21 24 23 23 23 23 3 1 1 1 1 1 1 12 10 10 10 10 10 18 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 20 19 19 19 19 19 19 19 19 19 19 22 21 21 21 21 21 21 24 23 23 23 23 23 23 23 2 1 1 1 1 1 1 8 5 5 5 18 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 20 19 19 19 19 19 19 19 19 22 21 21 21 24 23 23 23 23 23 20 19 19 19 19 19 19 19 22 21 21 21 21 21 21 21 21 24 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 23 2 1 1 1 8 18 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17 17];
  • 從新對齊的文件以下所示: 從新對齊結果
  • 經常使用的可選項爲--beam=16,調整參數能夠獲得不一樣的對齊結果。
/home/speech.AI/kaldi/src/gmmbin/gmm-align-compiled --beam=16 1.mdl ark:graphs_new.fsts ark:delta.ark ark,t:ali1.txt

這裏寫圖片描述

9. train_mono.sh 總體流程詳解

整個腳本的思想就是:

1.  gmm-init-mono 模型初始化
2. compile-train-graghs 訓練圖初始化
3. align-equal-compiled 特徵文件均勻分割
4. gmm-acc-stats-ali 累積模型重估所需數據
5. gmm-sum-accs 並行數據合併
6. gmm-est 聲音模型參數重估
7. gmm-boost-silence 模型平滑處理
8. gmm-align-compiled 特徵從新對齊
9. 重複n次執行:7->8->4->5->6(從新對齊->參數從新估計)
10. 輸出最終參數
#!/bin/bash
# Copyright 2012  Johns Hopkins University (Author: Daniel Povey)
# Apache 2.0


# To be run from ..
# Flat start and monophone training, with delta-delta features.
# This script applies cepstral mean normalization (per speaker).

# Begin configuration section.
nj=4
cmd=run.pl
scale_opts="--transition-scale=1.0 --acoustic-scale=0.1 --self-loop-scale=0.1"
num_iters=40    # Number of iterations of training   訓練迭代次數
max_iter_inc=30 # Last iter to increase #Gauss on.   高斯數遞增的最大次數
totgauss=1000 # Target #Gaussians.
careful=false
boost_silence=1.0 # Factor by which to boost silence likelihoods in alignment   強制改變某些音素的似然機率因子,見下面的代碼
realign_iters="1 2 3 4 5 6 7 8 9 10 12 14 16 18 20 23 26 29 32 35 38";
config= # name of config file.
stage=-4
power=0.25 # exponent to determine number of gaussians from occurrence counts 
norm_vars=false # deprecated, prefer --cmvn-opts "--norm-vars=false"   
cmvn_opts=  # can be used to add extra options to cmvn.   cmvn選項
# End configuration section.

echo "$0 $@"  # Print the command line for logging

if [ -f path.sh ]; then . ./path.sh; fi
. parse_options.sh || exit 1;

if [ $# != 3 ]; then
  echo "Usage: steps/train_mono.sh [options] <data-dir> <lang-dir> <exp-dir>"
  echo " e.g.: steps/train_mono.sh data/train.1k data/lang exp/mono"
  echo "main options (for others, see top of script file)"
  echo "  --config <config-file>                           # config containing options"
  echo "  --nj <nj>                                        # number of parallel jobs"
  echo "  --cmd (utils/run.pl|utils/queue.pl <queue opts>) # how to run jobs."
  exit 1;
fi

data=$1
lang=$2
dir=$3

oov_sym=`cat $lang/oov.int` || exit 1;#靜音符號表

# 按照任務數,將訓練數據分紅多份,每一個任務處理一份數據。
mkdir -p $dir/log
echo $nj > $dir/num_jobs
sdata=$data/split$nj;
[[ -d $sdata && $data/feats.scp -ot $sdata ]] || split_data.sh $data $nj || exit 1;

# 特徵歸一化選項,這裏默認指定要對variance進行歸一化,還可從外部接收其餘歸一化選項,若是外部指定不對variance進行歸一化,則外部指定生效。
$norm_vars && cmvn_opts="--norm-vars=true $cmvn_opts"
echo $cmvn_opts  > $dir/cmvn_opts # keep track of options to CMVN.

feats="ark,s,cs:apply-cmvn $cmvn_opts --utt2spk=ark:$sdata/JOB/utt2spk scp:$sdata/JOB/cmvn.scp scp:$sdata/JOB/feats.scp ark:- | add-deltas ark:- ark:- |"
example_feats="`echo $feats | sed s/JOB/1/g`";

echo "$0: Initializing monophone system."

[ ! -f $lang/phones/sets.int ] && exit 1;
shared_phones_opt="--shared-phones=$lang/phones/sets.int"

if [ $stage -le -3 ]; then
  # Note: JOB=1 just uses the 1st part of the features-- we only need a subset anyway.
  # 獲取特徵的維度
  if ! feat_dim=`feat-to-dim "$example_feats" - 2>/dev/null` || [ -z $feat_dim ]; then
    feat-to-dim "$example_feats" -
    echo "error getting feature dimension"
    exit 1;
  fi
  # Flat-start(又稱爲快速啓動),做用是利用少許的數據快速獲得一個初始化的 HMM-GMM 模型和決策樹
  # $lang/topo 中定義了每一個音素(phone)所對應的 HMM 模型狀態數以及初始時的轉移機率
  # --shared-phones=$lang/phones/sets.int 選項指向的文件,即$lang/phones/sets.int(該文件生成roots.txt中開頭爲share split的部分,表示同一行元素共享pdf,容許進行決策樹分裂),文件中同一行的音素(phone)共享 GMM 機率分佈。tree文件由sets.int產生。
  # --train-feats=$feats subset-feats --n=10 ark:- ark:-| 選項指定用來初始化訓練用的特徵,通常採用少許數據,程序內部會計算這批數據的means和variance,做爲初始高斯模型。sets.int中全部行的初始pdf都用這個計算出來的means和variance進行初始化。
  $cmd JOB=1 $dir/log/init.log \
    gmm-init-mono $shared_phones_opt "--train-feats=$feats subset-feats --n=10 ark:- ark:-|" $lang/topo $feat_dim \
    $dir/0.mdl $dir/tree || exit 1;
fi
# 計算當前高斯數,(目標高斯數 - 當前高斯數)/ 增長高斯迭代次數 獲得每次迭代須要增長的高斯數目
numgauss=`gmm-info --print-args=false $dir/0.mdl | grep gaussians | awk '{print $NF}'`
incgauss=$[($totgauss-$numgauss)/$max_iter_inc] # per-iter increment for #Gauss

# 構造訓練的網絡,從源碼級別分析,是每一個句子構造一個phone level 的fst網絡。
# $sdaba/JOB/text 中包含對每一個句子的單詞(words level)級別標註, L.fst是字典對於的fst表示,做用是將一串的音素(phones)轉換成單詞(words)
# 構造monophone解碼圖就是先將text中的每一個句子,生成一個fst(相似於語言模型中的G.fst,只是相對比較簡單,只有一個句子),而後和L.fst 進行composition 造成訓練用的音素級別(phone level)fst網絡(相似於LG.fst)。
# fsts.JOB.gz 中使用 key-value 的方式保存每一個句子和其對應的fst網絡,經過 key(句子) 就能找到這個句子的fst網絡,value中保存的是句子中每兩個音素之間互聯的邊(Arc),例如句子轉換成音素後,標註爲:"a b c d e f",那麼value中保存的實際上是 a->b b->c c->d d->e e->f 這些鏈接(kaldi會爲每種鏈接賦予一個惟一的id),後面進行 HMM 訓練的時候是根據這些鏈接的id進行計數,就能夠獲得轉移機率。
if [ $stage -le -2 ]; then
  echo "$0: Compiling training graphs"
  $cmd JOB=1:$nj $dir/log/compile_graphs.JOB.log \
    compile-train-graphs $dir/tree $dir/0.mdl  $lang/L.fst \
    "ark:sym2int.pl --map-oov $oov_sym -f 2- $lang/words.txt < $sdata/JOB/text|" \
    "ark:|gzip -c >$dir/fsts.JOB.gz" || exit 1;
fi

if [ $stage -le -1 ]; then
  echo "$0: Aligning data equally (pass 0)"
  $cmd JOB=1:$nj $dir/log/align.0.JOB.log \
# 訓練時須要將標註跟每一幀特徵進行對齊,因爲如今尚未能夠用於對齊的模型,因此採用最簡單的方法 -- 均勻對齊
# 根據標註數目對特徵序列進行等間隔切分,例如一個具備5個標註的長度爲100幀的特徵序列,則認爲1-20幀屬於第1個標註,21-40屬於第2個...
# 這種劃分方法雖然會有偏差,但待會在訓練模型的過程當中會不斷地從新對齊。
    align-equal-compiled "ark:gunzip -c $dir/fsts.JOB.gz|" "$feats" ark,t:-  \| \
# 對對齊後的數據進行訓練,得到中間統計量,每一個任務輸出到一個acc文件。
# acc中記錄跟HMM 和GMM 訓練相關的統計量:
# HMM 相關的統計量:兩個音素之間互聯的邊(Arc) 出現的次數。
#                 如上面所述,fst.JOB.gz 中每一個key對於的value保存一個句子中音素兩兩之間互聯的邊。
#                 gmm-acc-stats-ali 會統計每條邊(例如a->b)出現的次數,而後記錄到acc文件中。
# GMM 相關的統計量:每一個pdf-id 對應的特徵累計值和特徵平方累計值。
#                 對於每一幀,都會有個對齊後的標註,gmm-acc-stats-ali 能夠根據標註檢索獲得pdf-id,
#                 每一個pdf-id 對應的GMM可能由多個單高斯Component組成,會先計算在每一個單高斯Component對應的分佈下這一幀特徵的似然機率(log-likes),稱爲posterior。
#                 而後:
#                    (1)把每一個單高斯Component的posterior加到每一個高斯Component的occupancy(佔有率)計數器上,用於表徵特徵對於高斯的貢獻度,
#                        若是特徵一直落在某個高斯的分佈區間內,那對應的這個值就比較大;相反,若是一直落在區間外,則表示該高斯做用不大。
#                        gmm-est中能夠設置一個閾值,若是某個高斯的這個值低於閾值,則不更新其對應的高斯。
#                        另外這個值(向量)其實跟後面GMM更新時候的高斯權重weight的計算相關。
#                    (2)把這一幀數據加上每一個單高斯Component的posterior再加到每一個高斯的均值累計值上;
#                        這個值(向量)跟後面GMM的均值更新相關。
#                    (3)把這一幀數據的平方值加上posterior再加到每一個單高斯Component的平方累計值上;
#                        這個值(向量)跟後面GMM的方差更新相關。
#                 最後將均值累計值和平方累計值寫入到文件中。
    gmm-acc-stats-ali --binary=true $dir/0.mdl "$feats" ark:- \
    $dir/0.JOB.acc || exit 1;
fi

# In the following steps, the --min-gaussian-occupancy=3 option is important, otherwise
# we fail to est "rare" phones and later on, they never align properly.
# 根據上面獲得的統計量,更新每一個GMM模型,AccumDiagGmm中occupancy_的值決定混合高斯模型中每一個單高斯Component的weight;
# --min-gaussian-occupancy 的做用是設置occupancy_的閾值,若是某個單高斯Component的occupancy_低於這個閾值,那麼就不會更新這個高斯,
# 並且若是 --remove-low-count-gaussians=true,則對應得單高斯Component會被移除。
if [ $stage -le 0 ]; then
  gmm-est --min-gaussian-occupancy=3  --mix-up=$numgauss --power=$power \
    $dir/0.mdl "gmm-sum-accs - $dir/0.*.acc|" $dir/1.mdl 2> $dir/log/update.0.log || exit 1;
  rm $dir/0.*.acc
fi


beam=6 # will change to 10 below after 1st pass
# note: using slightly wider beams for WSJ vs. RM.
x=1
while [ $x -lt $num_iters ]; do
  echo "$0: Pass $x"
  if [ $stage -le $x ]; then
    if echo $realign_iters | grep -w $x >/dev/null; then
      echo "$0: Aligning data"
      # gmm-boost-silence 的做用是讓某些phones(由第一個參數指定)對應pdf的weight乘以--boost 參數所指定的數字,強行提升(若是大於1)/下降(若是小於1)這個phone的機率。
      # 若是多個phone共享同一個pdf,程序中會自動作去重,乘法操做只會執行一次。
      mdl="gmm-boost-silence --boost=$boost_silence `cat $lang/phones/optional_silence.csl` $dir/$x.mdl - |"
      # 執行force-alignment操做。
      # --self-loop-scale 和 --transition-scale 選項跟HMM 狀態跳轉相關,前者是設置自轉因子,後者是非自傳因子,能夠修改這兩個選項控制HMM的跳轉傾向。
      # --acoustic-scale 選項跟GMM輸出機率相關,用於平衡 GMM 輸出機率和 HMM 跳轉機率的重要性。
      # --beam 選項用於計算對解碼過程當中出現較低log-likelihood的token進行裁剪的閾值,該值設計的越小,大部分token會被裁剪以便提升解碼速度,但可能會在開始階段把正確的token裁剪掉致使沒法獲得正確的解碼路徑。
      # --retry-beam 選項用於修正上述的問題,當沒法獲得正確的解碼路徑後,會增長beam的值,若是找到了最佳解碼路徑則退出,不然一直增長指定該選項設置的值,若是還沒找到,就拋出警告,致使這種問題要麼是標註原本就不對,或者retry-beam也設計得過小。
      $cmd JOB=1:$nj $dir/log/align.$x.JOB.log \
        gmm-align-compiled $scale_opts --beam=$beam --retry-beam=$[$beam*4] --careful=$careful "$mdl" \
        "ark:gunzip -c $dir/fsts.JOB.gz|" "$feats" "ark,t:|gzip -c >$dir/ali.JOB.gz" \
        || exit 1;
    fi
       # 更新模型 
    $cmd JOB=1:$nj $dir/log/acc.$x.JOB.log \
      gmm-acc-stats-ali  $dir/$x.mdl "$feats" "ark:gunzip -c $dir/ali.JOB.gz|" \
      $dir/$x.JOB.acc || exit 1;

    $cmd $dir/log/update.$x.log \
      gmm-est --write-occs=$dir/$[$x+1].occs --mix-up=$numgauss --power=$power $dir/$x.mdl \
      "gmm-sum-accs - $dir/$x.*.acc|" $dir/$[$x+1].mdl || exit 1;
    rm $dir/$x.mdl $dir/$x.*.acc $dir/$x.occs 2>/dev/null
  fi
  # 線性增長混合高斯模型的數目,直到指定數量。
  if [ $x -le $max_iter_inc ]; then
     numgauss=$[$numgauss+$incgauss];
  fi
  # 提升裁剪門限。
  beam=10
  x=$[$x+1]
done

( cd $dir; rm final.{mdl,occs} 2>/dev/null; ln -s $x.mdl final.mdl; ln -s $x.occs final.occs )

utils/summarize_warnings.pl $dir/log

echo Done

# example of showing the alignments:
# show-alignments data/lang/phones.txt $dir/30.mdl "ark:gunzip -c $dir/ali.0.gz|" | head -4

大部份內容參考以下: 心胸決定格局...:Kaldi單音素模型 訓練部分

轉載請註明出處

相關文章
相關標籤/搜索