1f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
2f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// Licensed under the Apache License, Version 2.0 (the "License");
3f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// you may not use this file except in compliance with the License.
4f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// You may obtain a copy of the License at
5f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson//
6f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson//     http://www.apache.org/licenses/LICENSE-2.0
7f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson//
8f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// Unless required by applicable law or agreed to in writing, software
9f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// distributed under the License is distributed on an "AS IS" BASIS,
10f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// See the License for the specific language governing permissions and
12f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// limitations under the License.
13f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson//
14f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// Copyright 2005-2010 Google, Inc.
15f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// Author: jpr@google.com (Jake Ratkiewicz)
16f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
17f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson#ifndef FST_SCRIPT_FST_CLASS_H_
18f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson#define FST_SCRIPT_FST_CLASS_H_
19f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
20f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson#include <string>
21f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
22f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson#include <fst/fst.h>
23f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson#include <fst/mutable-fst.h>
24f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson#include <fst/vector-fst.h>
25f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson#include <iostream>
26f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson#include <fstream>
27dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin#include <sstream>
28f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
29f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// Classes to support "boxing" all existing types of FST arcs in a single
30f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// FstClass which hides the arc types. This allows clients to load
31f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// and work with FSTs without knowing the arc type.
32f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
33f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// These classes are only recommended for use in high-level scripting
34f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// applications. Most users should use the lower-level templated versions
35f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// corresponding to these classes.
36f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
37f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodsonnamespace fst {
38f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodsonnamespace script {
39f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
40f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson//
41f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// Abstract base class defining the set of functionalities implemented
42f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// in all impls, and passed through by all bases Below FstClassBase
43f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// the class hierarchy bifurcates; FstClassImplBase serves as the base
44f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// class for all implementations (of which FstClassImpl is currently
45f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// the only one) and FstClass serves as the base class for all
46f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// interfaces.
47f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson//
48f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodsonclass FstClassBase {
49f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson public:
50f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const string &ArcType() const = 0;
51f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const string &FstType() const = 0;
52f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const string &WeightType() const = 0;
53f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const SymbolTable *InputSymbols() const = 0;
54f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const SymbolTable *OutputSymbols() const = 0;
555b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin  virtual bool Write(const string& fname) const = 0;
565b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin  virtual bool Write(ostream &ostr, const FstWriteOptions &opts) const = 0;
57f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual uint64 Properties(uint64 mask, bool test) const = 0;
58f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual ~FstClassBase() { }
59f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson};
60f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
61f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodsonclass FstClassImplBase : public FstClassBase {
62f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson public:
63f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual FstClassImplBase *Copy() = 0;
64f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual void SetInputSymbols(SymbolTable *is) = 0;
65f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual void SetOutputSymbols(SymbolTable *is) = 0;
66f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual ~FstClassImplBase() { }
67f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson};
68f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
69f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
70f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson//
71f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// CONTAINER CLASS
72f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// Wraps an Fst<Arc>, hiding its arc type. Whether this Fst<Arc>
73f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// pointer refers to a special kind of FST (e.g. a MutableFst) is
74f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// known by the type of interface class that owns the pointer to this
75f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// container.
76f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson//
77f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
78f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodsontemplate<class Arc>
79f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodsonclass FstClassImpl : public FstClassImplBase {
80f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson public:
81f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  explicit FstClassImpl(Fst<Arc> *impl,
82f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson                        bool should_own = false) :
83f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      impl_(should_own ? impl : impl->Copy()) { }
84f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
855b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin  explicit FstClassImpl(const Fst<Arc> &impl) : impl_(impl.Copy()) {  }
865b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin
87f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const string &ArcType() const {
88f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return Arc::Type();
89f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
90f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
91f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const string &FstType() const {
92f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return impl_->Type();
93f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
94f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
95f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const string &WeightType() const {
96f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return Arc::Weight::Type();
97f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
98f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
99f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const SymbolTable *InputSymbols() const {
100f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return impl_->InputSymbols();
101f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
102f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
103f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const SymbolTable *OutputSymbols() const {
104f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return impl_->OutputSymbols();
105f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
106f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
107f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  // Warning: calling this method casts the FST to a mutable FST.
108f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual void SetInputSymbols(SymbolTable *is) {
109f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    static_cast<MutableFst<Arc> *>(impl_)->SetInputSymbols(is);
110f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
111f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
112f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  // Warning: calling this method casts the FST to a mutable FST.
113f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual void SetOutputSymbols(SymbolTable *os) {
114f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    static_cast<MutableFst<Arc> *>(impl_)->SetOutputSymbols(os);
115f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
116f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
1175b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin  virtual bool Write(const string &fname) const {
1185b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin    return impl_->Write(fname);
119f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
120f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
1215b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin  virtual bool Write(ostream &ostr, const FstWriteOptions &opts) const {
1225b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin    return impl_->Write(ostr, opts);
123dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin  }
124dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin
125f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual uint64 Properties(uint64 mask, bool test) const {
126f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return impl_->Properties(mask, test);
127f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
128f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
129f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual ~FstClassImpl() { delete impl_; }
130f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
131dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin  Fst<Arc> *GetImpl() const { return impl_; }
132dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin
133f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  Fst<Arc> *GetImpl() { return impl_; }
134f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
135f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual FstClassImpl *Copy() {
136f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return new FstClassImpl<Arc>(impl_);
137f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
138f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
139f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson private:
140f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  Fst<Arc> *impl_;
141f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson};
142f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
143f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson//
144f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// BASE CLASS DEFINITIONS
145f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson//
146f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
147f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodsonclass MutableFstClass;
148f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
149f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodsonclass FstClass : public FstClassBase {
150f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson public:
151f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
152f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  static FstClass *Read(istream &stream,
153f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson                        const FstReadOptions &opts) {
154f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    if (!opts.header) {
155f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      FSTERROR() << "FstClass::Read: options header not specified";
156f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      return 0;
157f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    }
158f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    const FstHeader &hdr = *opts.header;
159f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
160f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    if (hdr.Properties() & kMutable) {
161f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      return ReadTypedFst<MutableFstClass, MutableFst<Arc> >(stream, opts);
162f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    } else {
163f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      return ReadTypedFst<FstClass, Fst<Arc> >(stream, opts);
164f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    }
165f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
166f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
167dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin  FstClass() : impl_(NULL) {
168dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin  }
169dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin
170f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
1715b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin  explicit FstClass(const Fst<Arc> &fst) : impl_(new FstClassImpl<Arc>(fst)) {
172dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin  }
173f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
1745b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin  FstClass(const FstClass &other) : impl_(other.impl_->Copy()) { }
175f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
176dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin  FstClass &operator=(const FstClass &other) {
177dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin    delete impl_;
178dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin    impl_ = other.impl_->Copy();
179dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin    return *this;
180dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin  }
181dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin
182f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  static FstClass *Read(const string &fname);
183f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
184dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin  static FstClass *Read(istream &istr, const string &source);
185dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin
186f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const string &ArcType() const {
187f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return impl_->ArcType();
188f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
189f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
190f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const string& FstType() const {
191f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return impl_->FstType();
192f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
193f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
194f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const SymbolTable *InputSymbols() const {
195f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return impl_->InputSymbols();
196f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
197f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
198f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const SymbolTable *OutputSymbols() const {
199f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return impl_->OutputSymbols();
200f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
201f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
202f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual const string& WeightType() const {
203f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return impl_->WeightType();
204f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
205f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
2065b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin  virtual bool Write(const string &fname) const {
2075b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin    return impl_->Write(fname);
208f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
209f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
2105b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin  virtual bool Write(ostream &ostr, const FstWriteOptions &opts) const {
2115b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin    return impl_->Write(ostr, opts);
212dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin  }
213dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin
214f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual uint64 Properties(uint64 mask, bool test) const {
215f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return impl_->Properties(mask, test);
216f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
217f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
218f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
219f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  const Fst<Arc> *GetFst() const {
220f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    if (Arc::Type() != ArcType()) {
221f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      return NULL;
222f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    } else {
223f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      FstClassImpl<Arc> *typed_impl = static_cast<FstClassImpl<Arc> *>(impl_);
224f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      return typed_impl->GetImpl();
225f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    }
226f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
227f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
228f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual ~FstClass() { delete impl_; }
229f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
230f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  // These methods are required by IO registration
231f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
232f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  static FstClassImplBase *Convert(const FstClass &other) {
233f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    LOG(ERROR) << "Doesn't make sense to convert any class to type FstClass.";
234f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return 0;
235f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
236f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
237f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
238f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  static FstClassImplBase *Create() {
239f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    LOG(ERROR) << "Doesn't make sense to create an FstClass with a "
240f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson               << "particular arc type.";
241f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return 0;
242f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
243dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin
244dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin
245f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson protected:
246f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  explicit FstClass(FstClassImplBase *impl) : impl_(impl) { }
247f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
248f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  // Generic template method for reading an arc-templated FST of type
249f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  // UnderlyingT, and returning it wrapped as FstClassT, with appropriate
250f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  // error checking. Called from arc-templated Read() static methods.
251f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class FstClassT, class UnderlyingT>
252f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  static FstClassT* ReadTypedFst(istream &stream,
253f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson                                     const FstReadOptions &opts) {
254f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    UnderlyingT *u = UnderlyingT::Read(stream, opts);
255f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    if (!u) {
256f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      return 0;
257f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    } else {
2585b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin      FstClassT *r = new FstClassT(*u);
259f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      delete u;
260f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      return r;
261f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    }
262f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
263f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
264dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin  FstClassImplBase *GetImpl() const { return impl_; }
265dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin
266f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  FstClassImplBase *GetImpl() { return impl_; }
267dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin
268dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin//  friend ostream &operator<<(ostream&, const FstClass&);
269dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin
270f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson private:
271f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  FstClassImplBase *impl_;
272f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson};
273f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
274f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson//
275f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson// Specific types of FstClass with special properties
276f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson//
277f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
278f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodsonclass MutableFstClass : public FstClass {
279f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson public:
280f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
2815b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin  explicit MutableFstClass(const MutableFst<Arc> &fst) :
282f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      FstClass(fst) { }
283f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
284f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
285f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  MutableFst<Arc> *GetMutableFst() {
286f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    Fst<Arc> *fst = const_cast<Fst<Arc> *>(this->GetFst<Arc>());
287f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    MutableFst<Arc> *mfst = static_cast<MutableFst<Arc> *>(fst);
288f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
289f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return mfst;
290f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
291f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
292f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
293f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  static MutableFstClass *Read(istream &stream,
294f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson                               const FstReadOptions &opts) {
295f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    MutableFst<Arc> *mfst = MutableFst<Arc>::Read(stream, opts);
296f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    if (!mfst) {
297f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      return 0;
298f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    } else {
2995b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin      MutableFstClass *retval = new MutableFstClass(*mfst);
300f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      delete mfst;
301f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      return retval;
302f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    }
303f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
304f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
3055b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin  virtual bool Write(const string &fname) const {
3065b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin    return GetImpl()->Write(fname);
307dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin  }
308dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin
3095b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin  virtual bool Write(ostream &ostr, const FstWriteOptions &opts) const {
3105b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin    return GetImpl()->Write(ostr, opts);
311dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin  }
312dfd8b8327b93660601d016cdc6f29f433b45a8d8Alexander Gutkin
313f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  static MutableFstClass *Read(const string &fname, bool convert = false);
314f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
315f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual void SetInputSymbols(SymbolTable *is) {
316f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    GetImpl()->SetInputSymbols(is);
317f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
318f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
319f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  virtual void SetOutputSymbols(SymbolTable *os) {
320f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    GetImpl()->SetOutputSymbols(os);
321f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
322f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
323f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  // These methods are required by IO registration
324f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
325f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  static FstClassImplBase *Convert(const FstClass &other) {
326f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    LOG(ERROR) << "Doesn't make sense to convert any class to type "
327f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson               << "MutableFstClass.";
328f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return 0;
329f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
330f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
331f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
332f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  static FstClassImplBase *Create() {
333f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    LOG(ERROR) << "Doesn't make sense to create a MutableFstClass with a "
334f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson               << "particular arc type.";
335f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return 0;
336f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
337f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
338f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson protected:
339f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  explicit MutableFstClass(FstClassImplBase *impl) : FstClass(impl) { }
340f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson};
341f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
342f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
343f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodsonclass VectorFstClass : public MutableFstClass {
344f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson public:
345f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  explicit VectorFstClass(const FstClass &other);
346f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  explicit VectorFstClass(const string &arc_type);
347f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
348f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
3495b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin  explicit VectorFstClass(const VectorFst<Arc> &fst) :
350f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      MutableFstClass(fst) { }
351f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
352f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
353f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  static VectorFstClass *Read(istream &stream,
354f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson                              const FstReadOptions &opts) {
355f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    VectorFst<Arc> *vfst = VectorFst<Arc>::Read(stream, opts);
356f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    if (!vfst) {
357f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      return 0;
358f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    } else {
3595b6dc79427b8f7eeb6a7ff68034ab8548ce670eaAlexander Gutkin      VectorFstClass *retval = new VectorFstClass(*vfst);
360f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      delete vfst;
361f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson      return retval;
362f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    }
363f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
364f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
365f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  static VectorFstClass *Read(const string &fname);
366f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
367f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  // Converter / creator for known arc types
368f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
369f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  static FstClassImplBase *Convert(const FstClass &other) {
370f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return new FstClassImpl<Arc>(new VectorFst<Arc>(
371f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson        *other.GetFst<Arc>()), true);
372f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
373f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
374f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  template<class Arc>
375f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  static FstClassImplBase *Create() {
376f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson    return new FstClassImpl<Arc>(new VectorFst<Arc>(), true);
377f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson  }
378f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson};
379f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson
380f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson}  // namespace script
381f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson}  // namespace fst
382f4c12fce1ee58e670f9c3fce46c40296ba9ee8a2Ian Hodson#endif  // FST_SCRIPT_FST_CLASS_H_
383