FST  openfst-1.8.2.post1
OpenFst Library
shortest-distance.h
Go to the documentation of this file.
1 // Copyright 2005-2020 Google LLC
2 //
3 // Licensed under the Apache License, Version 2.0 (the 'License');
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 // http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an 'AS IS' BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 //
15 // See www.openfst.org for extensive documentation on this weighted
16 // finite-state transducer library.
17 
18 #ifndef FST_SCRIPT_SHORTEST_DISTANCE_H_
19 #define FST_SCRIPT_SHORTEST_DISTANCE_H_
20 
21 #include <cstdint>
22 #include <tuple>
23 #include <vector>
24 
25 #include <fst/queue.h>
26 #include <fst/shortest-distance.h>
28 #include <fst/script/arg-packs.h>
29 #include <fst/script/fst-class.h>
30 #include <fst/script/prune.h>
31 #include <fst/script/script-impl.h>
33 
34 namespace fst {
35 namespace script {
36 
40  const int64_t source;
41  const float delta;
42 
43  ShortestDistanceOptions(QueueType queue_type, ArcFilterType arc_filter_type,
44  int64_t source, float delta)
45  : queue_type(queue_type),
46  arc_filter_type(arc_filter_type),
47  source(source),
48  delta(delta) {}
49 };
50 
51 namespace internal {
52 
53 // Code to implement switching on queue and arc filter types.
54 
55 template <class Arc, class Queue, class ArcFilter>
57  using Weight = typename Arc::Weight;
58 
59  static std::unique_ptr<Queue> Construct(const Fst<Arc> &,
60  const std::vector<Weight> *) {
61  return std::make_unique<Queue>();
62  }
63 };
64 
65 // Specializations to support queues with different constructors.
66 
67 template <class Arc, class ArcFilter>
68 struct QueueConstructor<Arc, AutoQueue<typename Arc::StateId>, ArcFilter> {
69  using StateId = typename Arc::StateId;
70  using Weight = typename Arc::Weight;
71 
72  // template<class Arc, class ArcFilter>
73  static std::unique_ptr<AutoQueue<StateId>> Construct(
74  const Fst<Arc> &fst, const std::vector<Weight> *distance) {
75  return std::make_unique<AutoQueue<StateId>>(fst, distance, ArcFilter());
76  }
77 };
78 
79 template <class Arc, class ArcFilter>
81  Arc, NaturalShortestFirstQueue<typename Arc::StateId, typename Arc::Weight>,
82  ArcFilter> {
83  using StateId = typename Arc::StateId;
84  using Weight = typename Arc::Weight;
85 
86  static std::unique_ptr<NaturalShortestFirstQueue<StateId, Weight>> Construct(
87  const Fst<Arc> &, const std::vector<Weight> *distance) {
88  return std::make_unique<NaturalShortestFirstQueue<StateId, Weight>>(
89  *distance);
90  }
91 };
92 
93 template <class Arc, class ArcFilter>
94 struct QueueConstructor<Arc, TopOrderQueue<typename Arc::StateId>, ArcFilter> {
95  using StateId = typename Arc::StateId;
96  using Weight = typename Arc::Weight;
97 
98  static std::unique_ptr<TopOrderQueue<StateId>> Construct(
99  const Fst<Arc> &fst, const std::vector<Weight> *) {
100  return std::make_unique<TopOrderQueue<StateId>>(fst, ArcFilter());
101  }
102 };
103 
104 template <class Arc, class Queue, class ArcFilter>
106  std::vector<typename Arc::Weight> *distance,
107  const ShortestDistanceOptions &opts) {
108  std::unique_ptr<Queue> queue(
111  queue.get(), ArcFilter(), opts.source, opts.delta);
112  ShortestDistance(fst, distance, sopts);
113 }
114 
115 template <class Arc, class Queue>
117  std::vector<typename Arc::Weight> *distance,
118  const ShortestDistanceOptions &opts) {
119  switch (opts.arc_filter_type) {
120  case ArcFilterType::ANY: {
121  ShortestDistance<Arc, Queue, AnyArcFilter<Arc>>(fst, distance, opts);
122  return;
123  }
124  case ArcFilterType::EPSILON: {
125  ShortestDistance<Arc, Queue, EpsilonArcFilter<Arc>>(fst, distance, opts);
126  return;
127  }
129  ShortestDistance<Arc, Queue, InputEpsilonArcFilter<Arc>>(fst, distance,
130  opts);
131  return;
132  }
134  ShortestDistance<Arc, Queue, OutputEpsilonArcFilter<Arc>>(fst, distance,
135  opts);
136  return;
137  }
138  default: {
139  FSTERROR() << "ShortestDistance: Unknown arc filter type: "
140  << static_cast<std::underlying_type_t<ArcFilterType>>(
141  opts.arc_filter_type);
142  distance->clear();
143  distance->resize(1, Arc::Weight::NoWeight());
144  return;
145  }
146  }
147 }
148 
149 } // namespace internal
150 
152  std::tuple<const FstClass &, std::vector<WeightClass> *,
154 
155 template <class Arc>
157  using StateId = typename Arc::StateId;
158  using Weight = typename Arc::Weight;
159  const Fst<Arc> &fst = *std::get<0>(*args).GetFst<Arc>();
160  const auto &opts = std::get<2>(*args);
161  std::vector<Weight> typed_distance;
162  switch (opts.queue_type) {
163  case AUTO_QUEUE: {
164  internal::ShortestDistance<Arc, AutoQueue<StateId>>(fst, &typed_distance,
165  opts);
166  break;
167  }
168  case FIFO_QUEUE: {
169  internal::ShortestDistance<Arc, FifoQueue<StateId>>(fst, &typed_distance,
170  opts);
171  break;
172  }
173  case LIFO_QUEUE: {
174  internal::ShortestDistance<Arc, LifoQueue<StateId>>(fst, &typed_distance,
175  opts);
176  break;
177  }
178  case SHORTEST_FIRST_QUEUE: {
179  if constexpr (IsIdempotent<Weight>::value) {
182  fst, &typed_distance, opts);
183  } else {
184  FSTERROR() << "ShortestDistance: Bad queue type SHORTEST_FIRST_QUEUE"
185  << " for non-idempotent Weight " << Weight::Type();
186  }
187  break;
188  }
189  case STATE_ORDER_QUEUE: {
190  internal::ShortestDistance<Arc, StateOrderQueue<StateId>>(
191  fst, &typed_distance, opts);
192  break;
193  }
194  case TOP_ORDER_QUEUE: {
195  internal::ShortestDistance<Arc, TopOrderQueue<StateId>>(
196  fst, &typed_distance, opts);
197  break;
198  }
199  default: {
200  FSTERROR() << "ShortestDistance: Unknown queue type: " << opts.queue_type;
201  typed_distance.clear();
202  typed_distance.resize(1, Arc::Weight::NoWeight());
203  break;
204  }
205  }
206  internal::CopyWeights(typed_distance, std::get<1>(*args));
207 }
208 
210  std::tuple<const FstClass &, std::vector<WeightClass> *, bool, double>;
211 
212 template <class Arc>
214  using Weight = typename Arc::Weight;
215  const Fst<Arc> &fst = *std::get<0>(*args).GetFst<Arc>();
216  std::vector<Weight> typed_distance;
217  ShortestDistance(fst, &typed_distance, std::get<2>(*args),
218  std::get<3>(*args));
219  internal::CopyWeights(typed_distance, std::get<1>(*args));
220 }
221 
222 using FstShortestDistanceInnerArgs3 = std::tuple<const FstClass &, double>;
223 
226 
227 template <class Arc>
229  const Fst<Arc> &fst = *std::get<0>(args->args).GetFst<Arc>();
230  args->retval = WeightClass(ShortestDistance(fst, std::get<1>(args->args)));
231 }
232 
233 void ShortestDistance(const FstClass &fst, std::vector<WeightClass> *distance,
234  const ShortestDistanceOptions &opts);
235 
236 void ShortestDistance(const FstClass &ifst, std::vector<WeightClass> *distance,
237  bool reverse = false,
238  double delta = fst::kShortestDelta);
239 
241  double delta = fst::kShortestDelta);
242 
243 } // namespace script
244 } // namespace fst
245 
246 #endif // FST_SCRIPT_SHORTEST_DISTANCE_H_
QueueType
Definition: queue.h:70
std::tuple< const FstClass &, std::vector< WeightClass > *, bool, double > FstShortestDistanceArgs2
static std::unique_ptr< TopOrderQueue< StateId > > Construct(const Fst< Arc > &fst, const std::vector< Weight > *)
std::bool_constant<(W::Properties()&kIdempotent)!=0 > IsIdempotent
Definition: weight.h:156
void CopyWeights(const std::vector< WeightClass > &weights, std::vector< Weight > *typed_weights)
Definition: script-impl.h:202
static std::unique_ptr< AutoQueue< StateId > > Construct(const Fst< Arc > &fst, const std::vector< Weight > *distance)
#define FSTERROR()
Definition: util.h:53
void ShortestDistance(const Fst< Arc > &fst, std::vector< typename Arc::Weight > *distance, const ShortestDistanceOptions &opts)
static std::unique_ptr< Queue > Construct(const Fst< Arc > &, const std::vector< Weight > *)
static std::unique_ptr< NaturalShortestFirstQueue< StateId, Weight > > Construct(const Fst< Arc > &, const std::vector< Weight > *distance)
ShortestDistanceOptions(QueueType queue_type, ArcFilterType arc_filter_type, int64_t source, float delta)
constexpr float kShortestDelta
void ShortestDistance(FstShortestDistanceArgs1 *args)
std::tuple< const FstClass &, std::vector< WeightClass > *, const ShortestDistanceOptions & > FstShortestDistanceArgs1
std::tuple< const FstClass &, double > FstShortestDistanceInnerArgs3