2.1 data_prep.sh

首先检查格式和flac工具(原数据集是flac文件)
然后开始生成wav_scp、trans、utt2spk、spk2gender这四个文件,具体步骤是
wav_scp=$dst/wav.scp; [[ -f "$wav_scp" ]] && rm $wav_scp
trans=$dst/text; [[ -f "$trans" ]] && rm $trans
utt2spk=$dst/utt2spk; [[ -f "$utt2spk" ]] && rm $utt2spk
spk2gender=$dst/spk2gender; [[ -f $spk2gender ]] && rm $spk2gender
#首先定义这4个文件,如果存在就删除他们
for reader_dir in $(find -L $src -mindepth 1 -maxdepth 1 -type d | sort); do
#$(find -L $src -mindepth 1 -maxdepth 1 -type d | sort): 这部分命令会查找$src变量所指定的目录下所有的子目录。-L选项会跟随所有符号链接,-mindepth 1 -maxdepth 1指定查找深度为1,这意味着只会查找指定目录下的子目录,不会再向下查找。-type d表示只查找目录类型。这些找到的目录通过sort进行排序。然后将子目录名就被设置为了reader_dir,这也就是该音频的reader,以下是原始数据集的文件结构


reader=$(basename $reader_dir)
if ! [ $reader -eq $reader ]; then # not integer.#如果reader不是整数就报错
echo "$0: unexpected subdirectory name $reader"
exit 1;
fi
reader_gender=$(egrep "^$reader[ ]+\|" $spk_file | awk -F'|' '{gsub(/[ ]+/, ""); print tolower($2)}')
if [ "$reader_gender" != 'm' ] && [ "$reader_gender" != 'f' ]; then
echo "Unexpected gender: '$reader_gender'"
exit 1;
fi
#对于每一个说话者,从SPEAKERS.TXT文件中提取性别信息,如果性别不是'm'(男性)或者'f'(女性),就打印错误信息并退出。
for chapter_dir in $(find -L $reader_dir/ -mindepth 1 -maxdepth 1 -type d | sort); do
chapter=$(basename $chapter_dir)#对于每个reader目录下的章节进行类似处理
if ! [ "$chapter" -eq "$chapter" ]; then
echo "$0: unexpected chapter-subdirectory name $chapter"
exit 1;
fi
find -L $chapter_dir/ -iname "*.flac" | sort | xargs -I% basename % .flac | \
awk -v "dir=$chapter_dir" '{printf "lbi-%s flac -c -d -s %s/%s.flac |\n", $0, dir, $0}' >>$wav_scp || exit 1;
#find命令用于在 $chapter_dir 指定的目录及其子目录中查找所有扩展名为 .flac 的文件。-L 选项会让 find 命令跟随符号链接,而 -iname 选项会忽略文件名的大小写。sort: 将 find 命令找到的文件列表进行排序。xargs -I% basename % .flac: xargs 命令将输入的文件列表传递给 basename 命令。basename 命令用于删除文件路径,只留下文件名。这里,-I% 表示将 % 作为占位符使用,用来表示 xargs 命令输入的每一项。所以 basename % .flac 会删除每个文件名的路径和扩展名 .flac。
#awk -v "dir=$chapter_dir" '{printf "lbi-%s flac -c -d -s %s/%s.flac |\n", $0, dir, $0}': awk 命令用于处理每个已删除路径和扩展名的文件名。这里,-v "dir=$chapter_dir" 是将 $chapter_dir 传递给 awk 脚本的方法。在 awk 脚本中,printf 命令用于格式化输出字符串,$0 代表当前行的完整输入,也就是文件名。这段 awk 脚本的结果是 "lbi-文件名 flac -c -d -s 文件路径/文件名.flac |" 的形式。>>$wav_scp || exit 1;: >> 是重定向操作符,将前面的所有输出追加到 $wav_scp 指定的文件中。如果这个操作失败,|| exit 1 会使脚本立即退出,返回值为 1,表示发生了错误。

chapter_trans=$chapter_dir/${reader}-${chapter}.trans.txt #找到reader下该章节中的txt文件

if $prepare_text; then #如果上文该变量设置为true(实际为true)
[ ! -f $chapter_trans ] && echo "$0: expected file $chapter_trans to exist" && exit 1
#这行代码首先检查 $chapter_trans 指定的文件是否存在。如果文件不存在([ ! -f $chapter_trans ] 返回 true),那么将会打印一条错误消息,并使脚本以错误代码 1 退出。
sed -e 's/^/lbi\-/' $chapter_trans >> $trans
#这行命令使用 sed(流编辑器)在 $chapter_trans 指定的文件的每一行开始处添加字符串 "lbi-"。-e 参数指定了要执行的编辑命令,'s/^/lbi\-/' 是一个替换命令,^ 表示每一行的开始处。最后,>> $trans 将这个操作的结果追加到 $trans 文件中。
fi


#原始txt和生成的text文件
# NOTE: For now we are using per-chapter utt2spk. That is each chapter is considered
# to be a different speaker. This is done for simplicity and because we want
# e.g. the CMVN to be calculated per-chapter
awk -v "reader=$reader" -v "chapter=$chapter" '{printf "lbi-%s lbi-%s-%s\n", $1, reader, chapter}' \
<$chapter_trans >>$utt2spk || exit 1
#创建utt2spk文件,该文件是一个映射,记录每一个话语(utterance)是由哪一个说话者(speaker)说的。这里的说话者是以章节为单位的,即每一个章节都被视为不同的说话者。
#awk -v "reader=$reader" -v "chapter=$chapter" '{printf "lbi-%s lbi-%s-%s\n", $1, reader, chapter}': 这是一个awk命令,用于处理每一行输入。这里,-v "reader=$reader"和-v "chapter=$chapter"是将$reader和$chapter变量的值传递给awk脚本的方式。在awk脚本中,printf命令用于格式化输出字符串,$1代表当前行的第一个字段。这个awk脚本的结果是 "lbi-第一个字段 lbi-reader字段-chapter字段" 的形式。
#<$chapter_trans: 这部分命令将$chapter_trans文件作为awk命令的输入。
#>>$utt2spk || exit 1: >>是重定向操作符,将前面的所有输出追加到$utt2spk指定的文件中。如果这个操作失败,|| exit 1会使脚本立即退出,返回值为1,表示发生了错误。
#简单来说就是取chapter_trans文件的每一行的第一个字段,"lbi-%s lbi-%s-%s\n", $1, reader, chapter作为s1的内容,然后用reader和chapter补充后面两个占位符,写入utt2spk

# reader -> gender map (again using per-chapter granularity)
echo "lbi-${reader}-${chapter} $reader_gender" >>$spk2gender
#创建spk2gender文件,该文件是一个映射,记录每一个说话者(这里还是以章节为单位)的性别。

done
done
然后
utils/utt2spk_to_spk2utt.pl <$utt2spk >$spk2utt || exit 1:这一行使用一个Perl脚本将utt2spk文件转换为spk2utt文件(说话者到话语的映射)。
if $prepare_text; then ... fi:如果启用了文本准备,这一部分将检查转录文本的数量是否等于utt2spk的数量。如果不等,脚本会打印错误信息并退出。
utils/validate_data_dir.sh --no-feats $($prepare_text || echo "--no-text") $dst || exit 1:这一行使用一个验证脚本检查目标目录。这个验证脚本会检查数据是否符合Kaldi的要求。
该脚本结束

上面写的有一点点乱,后面的格式规整了很多
后续让我确定一下这个内容是否公司保密先....
要守公司规定啊