60 using namespace kaldi;
65 typedef kaldi::uint64 uint64;
70 "Convert the keywords into in-vocabulary words using the given phone\n" 71 "level edit distance fst (E.fst). The large lexicon (L2.fst) and\n" 72 "inverted small lexicon (L1'.fst) are also expected to be present. We\n" 73 "actually use the composed FST L2xE.fst to be more efficient. Ideally\n" 74 "we should have used L2xExL1'.fst but this is quite computationally\n" 75 "expensive at command level. Keywords.int is in the transcription\n" 76 "format. If kwlist-wspecifier is given, the program also prints out\n" 77 "the proxy fst in a format where each line is \"kwid weight proxy\".\n" 79 "Usage: generate-proxy-keywords [options] <L2xE.fst> <L1'.fst> \\\n" 80 " <keyword-rspecifier> <proxy-wspecifier> [kwlist-wspecifier] \n" 81 " e.g.: generate-proxy-keywords L2xE.fst L1'.fst ark:keywords.int \\\n" 82 " ark:proxy.fsts [ark,t:proxy.kwlist.txt]\n";
86 int32 max_states = 100000;
87 int32 phone_nbest = 50;
88 int32 proxy_nbest = 100;
89 double phone_beam = 5;
90 double proxy_beam = 5;
91 po.Register(
"phone-nbest", &phone_nbest,
"Prune KxL2xE transducer to only " 92 "contain top n phone sequences, -1 means all sequences.");
93 po.Register(
"proxy-nbest", &proxy_nbest,
"Prune KxL2xExL1' transducer to " 94 "only contain top n proxy keywords, -1 means all proxies.");
95 po.Register(
"phone-beam", &phone_beam,
"Prune KxL2xE transducer to the " 96 "given beam, -1 means no prune.");
97 po.Register(
"proxy-beam", &proxy_beam,
"Prune KxL2xExL1' transducer to the " 98 "given beam, -1 means no prune.");
99 po.Register(
"max-states", &max_states,
"Prune kxL2xExL1' transducer to the " 100 "given number of states, 0 means no prune.");
105 if (phone_nbest != -1 && phone_nbest <= 0) {
106 KALDI_ERR <<
"--phone-nbest must either be -1 or positive.";
109 if (proxy_nbest != -1 && proxy_nbest <= 0) {
110 KALDI_ERR <<
"--proxy-nbest must either be -1 or positive.";
113 if (phone_beam != -1 && phone_beam < 0) {
114 KALDI_ERR <<
"--phone-beam must either be -1 or non-negative.";
117 if (proxy_beam != -1 && proxy_beam <=0) {
118 KALDI_ERR <<
"--proxy-beam must either be -1 or non-negative.";
122 if (po.NumArgs() < 4 || po.NumArgs() > 5) {
127 std::string L2xE_filename = po.GetArg(1),
128 L1_filename = po.GetArg(2),
129 keyword_rspecifier = po.GetArg(3),
130 proxy_wspecifier = po.GetArg(4),
131 kwlist_wspecifier = po.GetOptArg(5);
141 for (; !keyword_reader.Done(); keyword_reader.Next()) {
142 std::string key = keyword_reader.Key();
143 std::vector<int32> keyword = keyword_reader.Value();
144 keyword_reader.FreeCurrent();
148 VectorFst<StdArc> proxy;
149 VectorFst<StdArc> tmp_proxy;
154 ArcSort(&proxy, OLabelCompare<StdArc>());
155 Compose(proxy, *L2xE, &tmp_proxy);
158 KALDI_VLOG(1) <<
"Project(KxL2xE, PROJECT_OUTPUT)";
159 Project(&tmp_proxy, PROJECT_OUTPUT);
160 if (phone_beam >= 0) {
161 KALDI_VLOG(1) <<
"Prune(KxL2xE, " << phone_beam <<
")";
162 Prune(&tmp_proxy, phone_beam);
164 if (phone_nbest > 0) {
165 KALDI_VLOG(1) <<
"ShortestPath(KxL2xE, " << phone_nbest <<
")";
166 RmEpsilon(&tmp_proxy);
167 ShortestPath(tmp_proxy, &proxy, phone_nbest,
true,
true);
168 tmp_proxy.DeleteStates();
170 Determinize(proxy, &tmp_proxy);
171 proxy.DeleteStates();
175 tmp_proxy.DeleteStates();
176 ArcSort(&proxy, OLabelCompare<StdArc>());
181 ArcSort(&proxy, OLabelCompare<StdArc>());
182 if (proxy_beam >= 0) {
187 ComposeFst<StdArc> lazy_compose(proxy, *L1);
188 proxy.DeleteStates();
190 KALDI_VLOG(1) <<
"Project(KxL2xExL1', PROJECT_OUTPUT)";
191 ProjectFst<StdArc> lazy_project(lazy_compose, PROJECT_OUTPUT);
195 KALDI_VLOG(1) <<
"Prune(KxL2xExL1', " << proxy_beam <<
")";
196 PruneSpecial(lazy_project, &tmp_proxy, proxy_beam, max_states);
200 Compose(proxy, *L1, &tmp_proxy);
201 proxy.DeleteStates();
203 KALDI_VLOG(1) <<
"Project(KxL2xExL1', PROJECT_OUTPUT)";
204 Project(&tmp_proxy, PROJECT_OUTPUT);
206 if (proxy_nbest > 0) {
207 KALDI_VLOG(1) <<
"ShortestPath(KxL2xExL1', " << proxy_nbest <<
")";
209 tmp_proxy.DeleteStates();
211 ShortestPath(proxy, &tmp_proxy, proxy_nbest,
true,
true);
212 proxy.DeleteStates();
215 RmEpsilon(&tmp_proxy);
217 Determinize(tmp_proxy, &proxy);
218 tmp_proxy.DeleteStates();
219 KALDI_VLOG(1) <<
"ArcSort(KxL2xExL1', OLabel)";
220 ArcSort(&proxy, fst::OLabelCompare<StdArc>());
223 proxy_writer.Write(key, proxy);
226 if (po.NumArgs() == 5) {
227 if (proxy.Properties(kAcyclic,
true) == 0) {
228 KALDI_WARN <<
"Proxy FST has cycles, skip printing paths for " << key;
230 vector<vector<StdArc::Label> > path;
231 vector<StdArc::Weight> weight;
233 vector<StdArc::Label>(), StdArc::Weight::One());
235 for (int32
i = 0;
i < path.size();
i++) {
236 vector<double> kwlist;
237 kwlist.push_back(static_cast<double>(weight[
i].Value()));
238 for (int32
j = 0;
j < path[
i].size();
j++) {
239 kwlist.push_back(static_cast<double>(path[
i][
j]));
241 kwlist_writer.Write(key, kwlist);
251 KALDI_LOG <<
"Done " << n_done <<
" keywords";
252 return (n_done != 0 ? 0 : 1);
253 }
catch(
const std::exception &e) {
254 std::cerr << e.what();
fst::StdArc::StateId StateId
This code computes Goodness of Pronunciation (GOP) and extracts phone-level pronunciation feature for...
void PruneSpecial(const Fst< Arc > &ifst, VectorFst< Arc > *ofst, typename Arc::Weight beam, size_t max_states)
The function PruneSpecial is like the standard OpenFst function "prune", except it does not expand th...
For an extended explanation of the framework of which grammar-fsts are a part, please see Support for...
A templated class for writing objects to an archive or script file; see The Table concept...
void MakeLinearAcceptor(const std::vector< I > &labels, MutableFst< Arc > *ofst)
Creates unweighted linear acceptor from symbol sequence.
The class ParseOptions is for parsing command-line options; see Parsing command-line options for more...
bool PrintProxyFstPath(const VectorFst< StdArc > &proxy, vector< vector< StdArc::Label > > *path, vector< StdArc::Weight > *weight, StdArc::StateId cur_state, vector< StdArc::Label > cur_path, StdArc::Weight cur_weight)
A templated class for reading objects sequentially from an archive or script file; see The Table conc...
fst::StdArc::Weight Weight
#define KALDI_ASSERT(cond)
void ReadFstKaldi(std::istream &is, bool binary, VectorFst< Arc > *fst)