lattice-determinize-phone-pruned.cc
Go to the documentation of this file.
1 // latbin/lattice-determinize-phone-pruned.cc
2 
3 // Copyright 2014 Guoguo Chen
4 // 2017 Vimal Manohar
5 
6 // See ../../COPYING for clarification regarding multiple authors
7 //
8 // Licensed under the Apache License, Version 2.0 (the "License");
9 // you may not use this file except in compliance with the License.
10 // You may obtain a copy of the License at
11 //
12 // http://www.apache.org/licenses/LICENSE-2.0
13 //
14 // THIS CODE IS PROVIDED *AS IS* BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15 // KIND, EITHER EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION ANY IMPLIED
16 // WARRANTIES OR CONDITIONS OF TITLE, FITNESS FOR A PARTICULAR PURPOSE,
17 // MERCHANTABLITY OR NON-INFRINGEMENT.
18 // See the Apache 2 License for the specific language governing permissions and
19 // limitations under the License.
20 #include "base/kaldi-common.h"
21 #include "hmm/transition-model.h"
22 #include "lat/kaldi-lattice.h"
24 #include "lat/lattice-functions.h"
25 #include "lat/push-lattice.h"
26 #include "util/common-utils.h"
27 
28 int main(int argc, char *argv[]) {
29  try {
30  using namespace kaldi;
31  typedef kaldi::int32 int32;
32 
33  const char *usage =
34  "Determinize lattices, keeping only the best path (sequence of\n"
35  "acoustic states) for each input-symbol sequence. This version does\n"
36  "phone inertion when doing a first pass determinization, it then\n"
37  "removes the inserted symbols and does a second pass determinization.\n"
38  "It also does pruning as part of the determinization algorithm, which\n"
39  "is more efficient and prevents blowup.\n"
40  "\n"
41  "Usage: lattice-determinize-phone-pruned [options] <model> \\\n"
42  " <lattice-rspecifier> <lattice-wspecifier>\n"
43  " e.g.: lattice-determinize-phone-pruned --acoustic-scale=0.1 \\\n"
44  " final.mdl ark:in.lats ark:det.lats\n";
45 
46  ParseOptions po(usage);
47  bool write_compact = true;
48  BaseFloat acoustic_scale = 1.0;
49  BaseFloat beam = 10.0;
51  opts.max_mem = 50000000;
52 
53  po.Register("write-compact", &write_compact,
54  "If true, write in normal (compact) form. "
55  "--write-compact=false allows you to retain frame-level "
56  "acoustic score information, but this requires the input "
57  "to be in non-compact form e.g. undeterminized lattice "
58  "straight from decoding.");
59  po.Register("acoustic-scale", &acoustic_scale, "Scaling factor for acoustic"
60  " likelihoods.");
61  po.Register("beam", &beam, "Pruning beam [applied after acoustic scaling].");
62  opts.Register(&po);
63  po.Read(argc, argv);
64 
65  if (po.NumArgs() != 3) {
66  po.PrintUsage();
67  exit(1);
68  }
69 
70  std::string model_rxfilename = po.GetArg(1),
71  lats_rspecifier = po.GetArg(2),
72  lats_wspecifier = po.GetArg(3);
73 
74  TransitionModel trans_model;
75  ReadKaldiObject(model_rxfilename, &trans_model);
76 
77  // Reads as regular lattice-- this is the form the determinization code
78  // accepts.
79  SequentialLatticeReader lat_reader(lats_rspecifier);
80 
81  CompactLatticeWriter compact_lat_writer;
82  LatticeWriter lat_writer;
83 
84  if (write_compact)
85  compact_lat_writer.Open(lats_wspecifier);
86  else
87  lat_writer.Open(lats_wspecifier);
88 
89  int32 n_done = 0, n_warn = 0;
90 
91  // depth stats (for diagnostics).
92  double sum_depth_in = 0.0,
93  sum_depth_out = 0.0, sum_t = 0.0;
94 
95  if (acoustic_scale == 0.0)
96  KALDI_ERR << "Do not use a zero acoustic scale (cannot be inverted)";
97 
98  for (; !lat_reader.Done(); lat_reader.Next()) {
99  std::string key = lat_reader.Key();
100  Lattice lat = lat_reader.Value();
101  lat_reader.FreeCurrent();
102 
103  KALDI_VLOG(2) << "Processing lattice " << key;
104 
105  // Compute a map from each (t, tid) to (sum_of_acoustic_scores, count)
106  unordered_map<std::pair<int32,int32>, std::pair<BaseFloat, int32>,
107  PairHasher<int32> > acoustic_scores;
108  if (!write_compact)
109  ComputeAcousticScoresMap(lat, &acoustic_scores);
110 
111  fst::ScaleLattice(fst::AcousticLatticeScale(acoustic_scale), &lat);
112 
113  CompactLattice det_clat;
115  trans_model, &lat, beam, &det_clat, opts)) {
116  KALDI_WARN << "For key " << key << ", determinization did not succeed"
117  "(partial output will be pruned tighter than the specified beam.)";
118  n_warn++;
119  }
120 
121  int32 t;
123  double depth = CompactLatticeDepth(det_clat, &t);
124  sum_depth_in += lat.NumStates();
125  sum_depth_out += depth * t;
126  sum_t += t;
127 
128  if (write_compact) {
129  fst::ScaleLattice(fst::AcousticLatticeScale(1.0/acoustic_scale), &det_clat);
130  compact_lat_writer.Write(key, det_clat);
131  } else {
132  Lattice out_lat;
133  fst::ConvertLattice(det_clat, &out_lat);
134 
135  // Replace each arc (t, tid) with the averaged acoustic score from
136  // the computed map
137  ReplaceAcousticScoresFromMap(acoustic_scores, &out_lat);
138  lat_writer.Write(key, out_lat);
139  }
140 
141  n_done++;
142  }
143 
144  if (sum_t != 0.0) {
145  KALDI_LOG << "Average input-lattice depth (measured at at state level) is "
146  << (sum_depth_in / sum_t) << ", output depth is "
147  << (sum_depth_out / sum_t) << ", over " << sum_t << " frames "
148  << " (average num-frames = " << (sum_t / n_done) << ").";
149  }
150  KALDI_LOG << "Done " << n_done << " lattices, determinization finished "
151  << "earlier than specified by the beam on " << n_warn << " of "
152  << "these.";
153  return (n_done != 0 ? 0 : 1);
154  } catch(const std::exception &e) {
155  std::cerr << e.what();
156  return -1;
157  }
158 }
This code computes Goodness of Pronunciation (GOP) and extracts phone-level pronunciation feature for...
Definition: chain.dox:20
bool Open(const std::string &wspecifier)
void PrintUsage(bool print_command_line=false)
Prints the usage documentation [provided in the constructor].
void ReplaceAcousticScoresFromMap(const unordered_map< std::pair< int32, int32 >, std::pair< BaseFloat, int32 >, PairHasher< int32 > > &acoustic_scores, Lattice *lat)
This function restores acoustic scores computed using the function ComputeAcousticScoresMap into the ...
A templated class for writing objects to an archive or script file; see The Table concept...
Definition: kaldi-table.h:368
kaldi::int32 int32
int main(int argc, char *argv[])
void Write(const std::string &key, const T &value) const
void Register(const std::string &name, bool *ptr, const std::string &doc)
void ReadKaldiObject(const std::string &filename, Matrix< float > *m)
Definition: kaldi-io.cc:832
std::vector< std::vector< double > > AcousticLatticeScale(double acwt)
float BaseFloat
Definition: kaldi-types.h:29
The class ParseOptions is for parsing command-line options; see Parsing command-line options for more...
Definition: parse-options.h:36
BaseFloat CompactLatticeDepth(const CompactLattice &clat, int32 *num_frames)
Returns the depth of the lattice, defined as the average number of arcs crossing any given frame...
void ScaleLattice(const std::vector< std::vector< ScaleFloat > > &scale, MutableFst< ArcTpl< Weight > > *fst)
Scales the pairs of weights in LatticeWeight or CompactLatticeWeight by viewing the pair (a...
void ConvertLattice(const ExpandedFst< ArcTpl< Weight > > &ifst, MutableFst< ArcTpl< CompactLatticeWeightTpl< Weight, Int > > > *ofst, bool invert)
Convert lattice from a normal FST to a CompactLattice FST.
A templated class for reading objects sequentially from an archive or script file; see The Table conc...
Definition: kaldi-table.h:287
fst::VectorFst< LatticeArc > Lattice
Definition: kaldi-lattice.h:44
int Read(int argc, const char *const *argv)
Parses the command line options and fills the ParseOptions-registered variables.
#define KALDI_ERR
Definition: kaldi-error.h:147
#define KALDI_WARN
Definition: kaldi-error.h:150
std::string GetArg(int param) const
Returns one of the positional parameters; 1-based indexing for argc/argv compatibility.
fst::VectorFst< CompactLatticeArc > CompactLattice
Definition: kaldi-lattice.h:46
int NumArgs() const
Number of positional parameters (c.f. argc-1).
void ComputeAcousticScoresMap(const Lattice &lat, unordered_map< std::pair< int32, int32 >, std::pair< BaseFloat, int32 >, PairHasher< int32 > > *acoustic_scores)
This function computes the mapping from the pair (frame-index, transition-id) to the pair (sum-of-aco...
#define KALDI_VLOG(v)
Definition: kaldi-error.h:156
void TopSortCompactLatticeIfNeeded(CompactLattice *clat)
Topologically sort the compact lattice if not already topologically sorted.
#define KALDI_LOG
Definition: kaldi-error.h:153
bool DeterminizeLatticePhonePrunedWrapper(const kaldi::TransitionModel &trans_model, MutableFst< kaldi::LatticeArc > *ifst, double beam, MutableFst< kaldi::CompactLatticeArc > *ofst, DeterminizeLatticePhonePrunedOptions opts)
This function is a wrapper of DeterminizeLatticePhonePruned() that works for Lattice type FSTs...
A hashing function-object for pairs of ints.
Definition: stl-utils.h:235