Vaucanson  1.4.1
fmp_to_rw.hxx
1 // fmp_to_rw.hxx: this file is part of the Vaucanson project.
2 //
3 // Vaucanson, a generic library for finite state machines.
4 //
5 // Copyright (C) 2005, 2006, 2008 The Vaucanson Group.
6 //
7 // This program is free software; you can redistribute it and/or
8 // modify it under the terms of the GNU General Public License
9 // as published by the Free Software Foundation; either version 2
10 // of the License, or (at your option) any later version.
11 //
12 // The complete GNU General Public Licence Notice can be found as the
13 // `COPYING' file in the root directory.
14 //
15 // The Vaucanson Group consists of people listed in the `AUTHORS' file.
16 //
17 #ifndef VCSN_ALGORITHMS_FMP_TO_RW_HXX
18 # define VCSN_ALGORITHMS_FMP_TO_RW_HXX
19 
20 # include <vaucanson/automata/concept/automata.hh>
21 # include <vaucanson/automata/concept/transducer.hh>
22 # include <vaucanson/algebra/concept/freemonoid_product.hh>
23 
24 # include <map>
25 
26 namespace vcsn
27 {
28 
29  template<typename S, typename T,
30  typename SS, typename TT,
31  typename Self>
32  void
33  do_fmp_to_rw(const vcsn::AutomataBase<S>&,
36  const vcsn::Element<S, T>& fmp,
38  {
39  typedef typename T::hstate_t hstate_t;
40  // Map source automaton's states with result's states
41  std::map<hstate_t, hstate_t> m;
42 
43  // Input FMP type
44  typedef vcsn::Element<S, T> FMP_t;
45 
46  // Output transducer type
47  typedef vcsn::Element<SS, TT> Trans_t;
48 
49  /*-------------------------.
50  | Creating the transducer. |
51  `-------------------------*/
52 
53  // Adding states
54  for (typename FMP_t::state_iterator St = fmp.states().begin();
55  St != fmp.states().end();
56  ++St)
57  m[*St] = res.add_state();
58 
59 
60  /*-------------------------.
61  | Setting initial states. |
62  `-------------------------*/
63 
64  for (typename FMP_t::initial_iterator St, next = fmp.initial().begin();
65  next != fmp.initial().end();)
66  {
67  //We need to store the next iterator before using the current one
68  //to avoid an invalid iterator after having called set_final.
69  //Indeed, set_final can delete the iterator if its second parameter
70  //is the zero of the serie.
71  St = next;
72  next++;
73  //Series to be created
74  typename Trans_t::series_set_elt_t s(res.structure().series());
75 
76  typename FMP_t::series_set_elt_t s_elt = fmp.get_initial(*St);
77  for_all_const_(FMP_t::series_set_elt_t::support_t, i, s_elt.supp())
78  {
79  typename Trans_t::semiring_elt_value_t::monoid_elt_value_t
80  output_monoid_value;
81  typename Trans_t::semiring_elt_t::semiring_elt_t weight;
82 
83  typename Trans_t::monoid_elt_value_t
84  input_monoid_value = (*i).first;
85  typename Trans_t::monoid_elt_t
86  input_monoid(res.structure().series().monoid(),
87  input_monoid_value);
88 
89  typename Trans_t::semiring_elt_t::monoid_elt_t
90  output_monoid(res.structure().series().semiring().monoid(),
91  (*i).second);
92  weight = s_elt.get(*i);
93 
94  //Creating the element multiplicity
95  typename Trans_t::semiring_elt_t
96  out_mult(res.structure().series().semiring());
97  out_mult.assoc(output_monoid, weight);
98 
99  //Associating it to the input monoid
100  s.assoc(input_monoid, out_mult);
101  }
102  res.set_initial(m[*St], s);
103  }
104 
105 
106  /*------------------------.
107  | Setting final states. |
108  `------------------------*/
109 
110  for (typename FMP_t::final_iterator St, next = fmp.final().begin();
111  next != fmp.final().end();)
112  {
113  //We need to store the next iterator before using the current one
114  //to avoid an invalid iterator after having called set_final.
115  //Indeed, set_final can delete the iterator if its second parameter
116  //is the zero of the serie.
117  St = next;
118  next++;
119  //Series to be created
120  typename Trans_t::series_set_elt_t s(res.structure().series());
121 
122  typename FMP_t::series_set_elt_t s_elt = fmp.get_final(*St);
123  for_all_const_(FMP_t::series_set_elt_t::support_t, i, s_elt.supp())
124  {
125  typename Trans_t::semiring_elt_value_t::monoid_elt_value_t
126  output_monoid_value;
127  typename Trans_t::semiring_elt_t::semiring_elt_t weight;
128 
129  typename Trans_t::monoid_elt_value_t input_monoid_value =
130  (*i).first;
131  typename Trans_t::monoid_elt_t
132  input_monoid(res.structure().series().monoid(),
133  input_monoid_value);
134  typename Trans_t::semiring_elt_t::monoid_elt_t
135  output_monoid(res.structure().series().semiring().monoid(),
136  (*i).second);
137  weight = s_elt.get(*i);
138 
139  //Creating the element multiplicity
140  typename Trans_t::semiring_elt_t
141  out_mult(res.structure().series().semiring());
142  out_mult.assoc(output_monoid, weight);
143 
144  //Associating it to the input monoid
145  s.assoc(input_monoid, out_mult);
146  }
147  res.set_final(m[*St], s);
148  }
149 
150 
151  /*-----------------------.
152  | Creating transitions. |
153  `-----------------------*/
154 
155  for (typename FMP_t::transition_iterator Ed = fmp.transitions().begin();
156  Ed != fmp.transitions().end();
157  ++Ed)
158  {
159  // FIXME
160  // No Special Treatment is done for 0 weighted
161  typename Trans_t::series_set_elt_t
162  transition_value(res.structure().series());
163 
164  typename Trans_t::monoid_elt_value_t input_monoid_value;
165  typename Trans_t::semiring_elt_value_t::monoid_elt_value_t
166  output_monoid_value;
167 
168  typename FMP_t::series_set_elt_t series_fmp(fmp.structure().series());
169  typename Trans_t::semiring_elt_t
170  out_mult(res.structure().series().semiring());
171  series_fmp = fmp.series_of(*Ed);
172 
173  for_all_const_(FMP_t::series_set_elt_t::support_t,
174  i,
175  series_fmp.supp())
176  {
177  input_monoid_value = (*i).first;
178  output_monoid_value = (*i).second;
179 
180  //Creating the transition's semiring value
181  typename Trans_t::semiring_elt_t::semiring_elt_t
182  transition_weight(res.structure().series().semiring().semiring(),
183  series_fmp.get(*i));
184  typename Trans_t::semiring_elt_t
185  out_mult(res.structure().series().semiring());
186  out_mult.assoc(typename Trans_t::semiring_elt_t::monoid_elt_t
187  (res.structure().series().semiring().monoid(),
188  output_monoid_value),
189  transition_weight);
190 
191  //Creating the transition's monoid value
192  typename Trans_t::monoid_elt_t
193  input(res.structure().series().monoid(),
194  input_monoid_value);
195  transition_value.assoc(input, out_mult);
196  res.add_series_transition(m[fmp.src_of(*Ed)],
197  m[fmp.dst_of(*Ed)],
198  transition_value);
199  }
200  }
201  }
202 
203  template<typename S, typename T,
204  typename SS, typename TT>
206  fmp_to_rw(const vcsn::Element<S, T>& fmp,
208  {
209  BENCH_TASK_SCOPED("fmp_to_rw");
210  do_fmp_to_rw(fmp.structure(), res.structure(),
211  fmp.structure().series().monoid(),
212  fmp, res);
213  return res;
214  }
215 }
216 #endif // ! VCSN_ALGORITHMS_FMP_TO_RW_HXX