kaldi-fst-io.cc
Go to the documentation of this file.
1 // fstext/kaldi-fst-io.cc
2 
3 // Copyright 2009-2011 Microsoft Corporation
4 // 2012-2015 Johns Hopkins University (Author: Daniel Povey)
5 // 2013 Guoguo Chen
6 
7 // See ../../COPYING for clarification regarding multiple authors
8 //
9 // Licensed under the Apache License, Version 2.0 (the "License");
10 // you may not use this file except in compliance with the License.
11 // You may obtain a copy of the License at
12 //
13 // http://www.apache.org/licenses/LICENSE-2.0
14 //
15 // THIS CODE IS PROVIDED *AS IS* BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16 // KIND, EITHER EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION ANY IMPLIED
17 // WARRANTIES OR CONDITIONS OF TITLE, FITNESS FOR A PARTICULAR PURPOSE,
18 // MERCHANTABLITY OR NON-INFRINGEMENT.
19 // See the Apache 2 License for the specific language governing permissions and
20 // limitations under the License.
21 
22 #include "fstext/kaldi-fst-io.h"
23 #include "base/kaldi-error.h"
24 #include "base/kaldi-math.h"
25 #include "util/kaldi-io.h"
26 
27 namespace fst {
28 
29 VectorFst<StdArc> *ReadFstKaldi(std::string rxfilename) {
30  if (rxfilename == "") rxfilename = "-"; // interpret "" as stdin,
31  // for compatibility with OpenFst conventions.
32  kaldi::Input ki(rxfilename);
33  fst::FstHeader hdr;
34  if (!hdr.Read(ki.Stream(), rxfilename))
35  KALDI_ERR << "Reading FST: error reading FST header from "
36  << kaldi::PrintableRxfilename(rxfilename);
37  FstReadOptions ropts("<unspecified>", &hdr);
38  VectorFst<StdArc> *fst = VectorFst<StdArc>::Read(ki.Stream(), ropts);
39  if (!fst)
40  KALDI_ERR << "Could not read fst from "
41  << kaldi::PrintableRxfilename(rxfilename);
42  return fst;
43 }
44 
45 Fst<StdArc> *ReadFstKaldiGeneric(std::string rxfilename, bool throw_on_err) {
46  if (rxfilename == "") rxfilename = "-"; // interpret "" as stdin,
47  // for compatibility with OpenFst conventions.
48  kaldi::Input ki(rxfilename);
49  fst::FstHeader hdr;
50  // Read FstHeader which contains the type of FST
51  if (!hdr.Read(ki.Stream(), rxfilename)) {
52  if(throw_on_err) {
53  KALDI_ERR << "Reading FST: error reading FST header from "
54  << kaldi::PrintableRxfilename(rxfilename);
55  } else {
56  KALDI_WARN << "We fail to read FST header from "
57  << kaldi::PrintableRxfilename(rxfilename)
58  << ". A NULL pointer is returned.";
59  return NULL;
60  }
61  }
62  // Check the type of Arc
63  if (hdr.ArcType() != fst::StdArc::Type()) {
64  if(throw_on_err) {
65  KALDI_ERR << "FST with arc type " << hdr.ArcType() << " is not supported.";
66  } else {
67  KALDI_WARN << "Fst with arc type" << hdr.ArcType()
68  << " is not supported. A NULL pointer is returned.";
69  return NULL;
70  }
71  }
72  // Read the FST
73  FstReadOptions ropts("<unspecified>", &hdr);
74  Fst<StdArc> *fst = NULL;
75  if (hdr.FstType() == "const") {
76  fst = ConstFst<StdArc>::Read(ki.Stream(), ropts);
77  } else if (hdr.FstType() == "vector") {
78  fst = VectorFst<StdArc>::Read(ki.Stream(), ropts);
79  }
80  if (!fst) {
81  if(throw_on_err) {
82  KALDI_ERR << "Could not read fst from "
83  << kaldi::PrintableRxfilename(rxfilename);
84  } else {
85  KALDI_WARN << "Could not read fst from "
86  << kaldi::PrintableRxfilename(rxfilename)
87  << ". A NULL pointer is returned.";
88  return NULL;
89  }
90  }
91  return fst;
92 }
93 
94 VectorFst<StdArc> *CastOrConvertToVectorFst(Fst<StdArc> *fst) {
95  // This version currently supports ConstFst<StdArc> or VectorFst<StdArc>
96  std::string real_type = fst->Type();
97  KALDI_ASSERT(real_type == "vector" || real_type == "const");
98  if (real_type == "vector") {
99  return dynamic_cast<VectorFst<StdArc> *>(fst);
100  } else {
101  // As the 'fst' can't cast to VectorFst, we create a new
102  // VectorFst<StdArc> initialized by 'fst', and delete 'fst'.
103  VectorFst<StdArc> *new_fst = new VectorFst<StdArc>(*fst);
104  delete fst;
105  return new_fst;
106  }
107 }
108 
109 void ReadFstKaldi(std::string rxfilename, fst::StdVectorFst *ofst) {
110  fst::StdVectorFst *fst = ReadFstKaldi(rxfilename);
111  *ofst = *fst;
112  delete fst;
113 }
114 
115 void WriteFstKaldi(const VectorFst<StdArc> &fst,
116  std::string wxfilename) {
117  if (wxfilename == "") wxfilename = "-"; // interpret "" as stdout,
118  // for compatibility with OpenFst conventions.
119  bool write_binary = true, write_header = false;
120  kaldi::Output ko(wxfilename, write_binary, write_header);
121  FstWriteOptions wopts(kaldi::PrintableWxfilename(wxfilename));
122  fst.Write(ko.Stream(), wopts);
123 }
124 
125 fst::VectorFst<fst::StdArc> *ReadAndPrepareLmFst(std::string rxfilename) {
126  // ReadFstKaldi() will die with exception on failure.
127  fst::VectorFst<fst::StdArc> *ans = fst::ReadFstKaldi(rxfilename);
128  if (ans->Properties(fst::kAcceptor, true) == 0) {
129  // If it's not already an acceptor, project on the output, i.e. copy olabels
130  // to ilabels. Generally the G.fst's on disk will have the disambiguation
131  // symbol #0 on the input symbols of the backoff arc, and projection will
132  // replace them with epsilons which is what is on the output symbols of
133  // those arcs.
134  fst::Project(ans, fst::PROJECT_OUTPUT);
135  }
136  if (ans->Properties(fst::kILabelSorted, true) == 0) {
137  // Make sure LM is sorted on ilabel.
138  fst::ILabelCompare<fst::StdArc> ilabel_comp;
139  fst::ArcSort(ans, ilabel_comp);
140  }
141  return ans;
142 }
143 
144 } // end namespace fst
Fst< StdArc > * ReadFstKaldiGeneric(std::string rxfilename, bool throw_on_err)
Definition: kaldi-fst-io.cc:45
For an extended explanation of the framework of which grammar-fsts are a part, please see Support for...
Definition: graph.dox:21
fst::StdVectorFst StdVectorFst
std::istream & Stream()
Definition: kaldi-io.cc:826
std::ostream & Stream()
Definition: kaldi-io.cc:701
fst::VectorFst< fst::StdArc > * ReadAndPrepareLmFst(std::string rxfilename)
#define KALDI_ERR
Definition: kaldi-error.h:147
#define KALDI_WARN
Definition: kaldi-error.h:150
#define KALDI_ASSERT(cond)
Definition: kaldi-error.h:185
void WriteFstKaldi(std::ostream &os, bool binary, const VectorFst< Arc > &t)
void ReadFstKaldi(std::istream &is, bool binary, VectorFst< Arc > *fst)
std::string PrintableRxfilename(const std::string &rxfilename)
PrintableRxfilename turns the rxfilename into a more human-readable form for error reporting...
Definition: kaldi-io.cc:61
std::string PrintableWxfilename(const std::string &wxfilename)
PrintableWxfilename turns the wxfilename into a more human-readable form for error reporting...
Definition: kaldi-io.cc:73
VectorFst< StdArc > * CastOrConvertToVectorFst(Fst< StdArc > *fst)
Definition: kaldi-fst-io.cc:94