1 2// Licensed under the Apache License, Version 2.0 (the "License"); 3// you may not use this file except in compliance with the License. 4// You may obtain a copy of the License at 5// 6// http://www.apache.org/licenses/LICENSE-2.0 7// 8// Unless required by applicable law or agreed to in writing, software 9// distributed under the License is distributed on an "AS IS" BASIS, 10// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 11// See the License for the specific language governing permissions and 12// limitations under the License. 13// 14// Copyright 2005-2010 Google, Inc. 15// Author: jpr@google.com (Jake Ratkiewicz) 16 17// These classes are only recommended for use in high-level scripting 18// applications. Most users should use the lower-level templated versions 19// corresponding to these classes. 20 21#include <fst/script/fst-class.h> 22#include <fst/script/register.h> 23#include <fst/fst-decl.h> 24#include <fst/union.h> 25#include <fst/reverse.h> 26#include <fst/equal.h> 27 28namespace fst { 29namespace script { 30 31// 32// REGISTRATION 33// 34 35REGISTER_FST_CLASSES(StdArc); 36REGISTER_FST_CLASSES(LogArc); 37REGISTER_FST_CLASSES(Log64Arc); 38 39// 40// FST CLASS METHODS 41// 42 43template<class FstT> 44FstT *ReadFst(istream &in, const string &fname) { 45 if (!in) { 46 LOG(ERROR) << "ReadFst: Can't open file: " << fname; 47 return 0; 48 } 49 50 FstHeader hdr; 51 if (!hdr.Read(in, fname)) { 52 return 0; 53 } 54 55 FstReadOptions read_options(fname, &hdr); 56 57 typename IORegistration<FstT>::Register *reg = 58 IORegistration<FstT>::Register::GetRegister(); 59 60 const typename IORegistration<FstT>::Reader reader = 61 reg->GetReader(hdr.ArcType()); 62 63 if (!reader) { 64 LOG(ERROR) << "ReadFst : unknown arc type \"" 65 << hdr.ArcType() << "\" : " << read_options.source; 66 return 0; 67 } 68 69 return reader(in, read_options); 70} 71 72FstClass *FstClass::Read(const string &fname) { 73 if (!fname.empty()) { 74 ifstream in(fname.c_str(), ifstream::in | ifstream::binary); 75 return ReadFst<FstClass>(in, fname); 76 } else { 77 return ReadFst<FstClass>(cin, "standard input"); 78 } 79} 80 81FstClass *FstClass::Read(istream &istr, const string &source) { 82 return ReadFst<FstClass>(istr, source); 83} 84 85// 86// MUTABLE FST CLASS METHODS 87// 88 89MutableFstClass *MutableFstClass::Read(const string &fname, bool convert) { 90 if (convert == false) { 91 if (!fname.empty()) { 92 ifstream in(fname.c_str(), ifstream::in | ifstream::binary); 93 return ReadFst<MutableFstClass>(in, fname); 94 } else { 95 return ReadFst<MutableFstClass>(cin, "standard input"); 96 } 97 } else { // Converts to VectorFstClass if not mutable. 98 FstClass *ifst = FstClass::Read(fname); 99 if (!ifst) return 0; 100 if (ifst->Properties(fst::kMutable, false)) { 101 return static_cast<MutableFstClass *>(ifst); 102 } else { 103 MutableFstClass *ofst = new VectorFstClass(*ifst); 104 delete ifst; 105 return ofst; 106 } 107 } 108} 109 110// 111// VECTOR FST CLASS METHODS 112// 113 114IORegistration<VectorFstClass>::Entry GetVFSTRegisterEntry( 115 const string &arc_type) { 116 IORegistration<VectorFstClass>::Register *reg = 117 IORegistration<VectorFstClass>::Register::GetRegister(); 118 const IORegistration<VectorFstClass>::Entry &entry = reg->GetEntry(arc_type); 119 120 if (entry.converter == 0) { 121 LOG(ERROR) << "Unknown arc type " << arc_type; 122 return entry; 123 } 124 125 return entry; 126} 127 128VectorFstClass::VectorFstClass(const FstClass &other) 129 : MutableFstClass(GetVFSTRegisterEntry(other.ArcType()).converter(other)) { 130} 131 132VectorFstClass::VectorFstClass(const string &arc_type) 133 : MutableFstClass(GetVFSTRegisterEntry(arc_type).creator()) { } 134 135VectorFstClass *VectorFstClass::Read(const string &fname) { 136 if (!fname.empty()) { 137 ifstream in(fname.c_str(), ifstream::in | ifstream::binary); 138 return ReadFst<VectorFstClass>(in, fname); 139 } else { 140 return ReadFst<VectorFstClass>(cin, "standard input"); 141 } 142} 143 144} // namespace script 145} // namespace fst 146