Vaucanson 1.4
decorated_alphabet.hxx
00001 // decorated_alphabet.hxx: this file is part of the Vaucanson project.
00002 //
00003 // Vaucanson, a generic library for finite state machines.
00004 //
00005 // Copyright (C) 2001, 2002, 2003, 2004, 2005, 2007 The Vaucanson Group.
00006 //
00007 // This program is free software; you can redistribute it and/or
00008 // modify it under the terms of the GNU General Public License
00009 // as published by the Free Software Foundation; either version 2
00010 // of the License, or (at your option) any later version.
00011 //
00012 // The complete GNU General Public Licence Notice can be found as the
00013 // `COPYING' file in the root directory.
00014 //
00015 // The Vaucanson Group consists of people listed in the `AUTHORS' file.
00016 //
00017 #ifndef VCSN_ALGEBRA_IMPLEMENTATION_ALPHABETS_DECORATED_ALPHABET_HXX
00018 # define VCSN_ALGEBRA_IMPLEMENTATION_ALPHABETS_DECORATED_ALPHABET_HXX
00019 
00020 # include <vaucanson/algebra/concept/letter.hh>
00021 # include <vaucanson/algebra/implementation/alphabets/decorated_alphabet.hh>
00022 
00023 namespace vcsn {
00024 
00025   namespace algebra
00026   {
00027     template <typename L, typename T>
00028     AlphabetDecorator<L, T>::~AlphabetDecorator()
00029     {
00030       if (alphabet_owner_)
00031         delete alphabet_;
00032     }
00033 
00034     template <typename L, typename T>
00035     AlphabetDecorator<L, T>::AlphabetDecorator()
00036     {
00037       alphabet_ = new T();
00038       joker_ = letter_traits<L>::default_joker;
00039       other_ =  letter_traits<L>::default_other;
00040       alphabet_owner_ = true;
00041     }
00042 
00043     template <typename L, typename T>
00044     AlphabetDecorator<L, T>::AlphabetDecorator(alphabet_impl_t& alphabet) :
00045       alphabet_(&alphabet)
00046     {
00047       alphabet_owner_ = false;
00048       if (std::find(alphabet.begin(), alphabet.end(),
00049                     letter_traits<L>::default_joker())
00050           == alphabet.end())
00051         joker_ = letter_traits<L>::default_joker();
00052       else
00053         {
00054           joker_ = letter_traits<L>::default_joker();
00055           do {
00056             ++joker_;
00057             if (joker_ == letter_traits<L>::default_joker())
00058               {
00059                 std::cerr << "Did not find a valid 'joker' ! Exiting !"
00060                           << std::endl;
00061                 exit(EXIT_FAILURE);
00062               }
00063           } while (std::find(alphabet.begin(), alphabet.end(),
00064                              joker_) != alphabet.end());
00065         }
00066       if (std::find(alphabet.begin(), alphabet.end(),
00067                     letter_traits<L>::default_other())
00068           == alphabet.end())
00069         other_ = letter_traits<L>::default_other();
00070       else
00071         {
00072           other_ = letter_traits<L>::default_other();
00073           do {
00074             ++other_;
00075             if (other_ == letter_traits<L>::default_other())
00076               {
00077                 std::cerr << "Did not find a valid 'other' ! Exiting !"
00078                           << std::endl;
00079                 exit(EXIT_FAILURE);
00080               }
00081           } while (std::find(alphabet.begin(), alphabet.end(),
00082                              other_) != alphabet.end());
00083         }
00084     }
00085 
00086     template <typename L, typename T>
00087     void
00088     AlphabetDecorator<L, T>::insert(L l)
00089     {
00090       alphabet().insert(l);
00091     }
00092 
00093 
00094     template <typename L, typename T>
00095     unsigned
00096     AlphabetDecorator<L, T>::size() const
00097     {
00098       return alphabet().size();
00099     }
00100 
00101     template <typename L, typename T>
00102     typename AlphabetDecorator<L, T>::iterator
00103     AlphabetDecorator<L, T>::begin()
00104     {
00105       return alphabet().begin();
00106     }
00107 
00108     template <typename L, typename T>
00109     typename AlphabetDecorator<L, T>::iterator
00110     AlphabetDecorator<L, T>::end()
00111     {
00112       return alphabet().end();
00113     }
00114 
00115     template <typename L, typename T>
00116     typename AlphabetDecorator<L, T>::const_iterator
00117     AlphabetDecorator<L, T>::begin() const
00118     {
00119       return alphabet().begin();
00120     }
00121 
00122     template <typename L, typename T>
00123     typename AlphabetDecorator<L, T>::const_iterator
00124     AlphabetDecorator<L, T>::end() const
00125     {
00126       return alphabet().end();
00127     }
00128 
00129     template <typename L, typename T>
00130     const T& AlphabetDecorator<L, T>::alphabet() const
00131     {
00132       return *alphabet_;
00133     }
00134 
00135     template <typename L, typename T>
00136     T& AlphabetDecorator<L, T>::alphabet()
00137     {
00138       return *alphabet_;
00139     }
00140 
00141     template <typename L, typename T>
00142     L AlphabetDecorator<L, T>::joker() const
00143     {
00144       return joker_;
00145     }
00146 
00147     template <typename L, typename T>
00148     L AlphabetDecorator<L, T>::other() const
00149     {
00150       return other_;
00151     }
00152   }
00153 
00154   template <typename L, typename T>
00155   L MetaElement<algebra::AlphabetSet<L>, algebra::AlphabetDecorator<L, T> >::
00156   joker() const
00157   {
00158     return this->value().joker();
00159   }
00160 
00161   template <typename L, typename T>
00162   L MetaElement<algebra::AlphabetSet<L>, algebra::AlphabetDecorator<L, T> >::
00163   other() const
00164   {
00165     return this->value().other();
00166   }
00167 
00168   namespace algebra {
00169 
00170     /*--------------------------------------------------.
00171     | Definition of an alphabet implementation based on |
00172     | AlphabetDecorator                                 |
00173     `--------------------------------------------------*/
00174 
00175     template <typename L, typename T>
00176     bool op_contains(const algebra::AlphabetSet<L>& s,
00177                      const algebra::AlphabetDecorator<L, T>& a)
00178     {
00179       return true;
00180     }
00181 
00182     template <typename L, typename T>
00183     bool op_is_finite(const algebra::AlphabetSet<L>& s,
00184                       const algebra::AlphabetDecorator<L, T>& a)
00185     {
00186       return true;
00187     }
00188 
00189     template <typename L, typename T>
00190     bool op_contains_e(const algebra::AlphabetSet<L>& s,
00191                        const algebra::AlphabetDecorator<L, T>& a,
00192                        const L& v)
00193     {
00194       if (v == a.joker())
00195         return true;
00196       if (v == a.other())
00197         return false;
00198       return Element<algebra::AlphabetSet<L>, T>(s, a.alphabet()).contains(v);
00199     }
00200 
00201     template <typename T, typename L>
00202     bool op_letter_equality(const algebra::AlphabetSet<L>& s,
00203                             const algebra::AlphabetDecorator<L, T>& a,
00204                             L lhs,
00205                             L rhs)
00206     {
00207       Element<algebra::AlphabetSet<L>,
00208               algebra::AlphabetDecorator<L, T> > e(s, a);
00209       if (lhs == a.joker())
00210         return e.contains(rhs);
00211       if (rhs == a.joker())
00212         return e.contains(lhs);
00213       if (lhs == a.other())
00214         return ! e.contains(rhs);
00215       if (rhs == a.other())
00216         return ! e.contains(lhs);
00217       return lhs == rhs;
00218     }
00219 
00220   } // algebra
00221 
00222 } // vcsn
00223 
00224 #endif // ! VCSN_ALGEBRA_IMPLEMENTATION_ALPHABETS_DECORATED_ALPHABET_HXX