cycle.hh

00001 // Copyright (C) 2001, 2002, 2003  EPITA Research and Development Laboratory
00002 //
00003 // This file is part of the Olena Library.  This library is free
00004 // software; you can redistribute it and/or modify it under the terms
00005 // of the GNU General Public License version 2 as published by the
00006 // Free Software Foundation.
00007 //
00008 // This library is distributed in the hope that it will be useful,
00009 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00010 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00011 // General Public License for more details.
00012 //
00013 // You should have received a copy of the GNU General Public License
00014 // along with this library; see the file COPYING.  If not, write to
00015 // the Free Software Foundation, 59 Temple Place - Suite 330, Boston,
00016 // MA 02111-1307, USA.
00017 //
00018 // As a special exception, you may use this file as part of a free
00019 // software library without restriction.  Specifically, if other files
00020 // instantiate templates or use macros or inline functions from this
00021 // file, or you compile this file and link it with other files to
00022 // produce an executable, this file does not by itself cause the
00023 // resulting executable to be covered by the GNU General Public
00024 // License.  This exception does not however invalidate any other
00025 // reasons why the executable file might be covered by the GNU General
00026 // Public License.
00027 
00028 #ifndef NTG_REAL_CYCLE_HH
00029 # define NTG_REAL_CYCLE_HH
00030 
00031 # include <ntg/basics.hh>
00032 # include <ntg/core/internal/macros.hh>
00033 # include <ntg/core/interval.hh>
00034 
00035 # include <mlc/is_a.hh>
00036 
00037 # include <string>
00038 # include <sstream>
00039 
00040 namespace ntg {
00041 
00042   namespace internal {
00043 
00044     /*------------------.
00045     | typetraits<cycle> |
00046     `------------------*/
00047 
00048     template <class T, class interval>
00049     struct typetraits<cycle<T, interval> > : public typetraits<T>
00050     {
00051       typedef cycle<T, interval>                        self;
00052       typedef typename typetraits<T>::abstract_type     abstract_type;
00053       typedef self                                      ntg_type;
00054       typedef optraits<self>                            optraits_type;
00055       typedef cycle_behavior::get<self>                 behavior_type;
00056       typedef cycle_behavior                            abstract_behavior_type;
00057 
00058       typedef typename typetraits<T>::base_type         base_type;
00059       typedef T                                         storage_type;
00060       typedef typename typetraits<T>::signed_type       signed_type;
00061       typedef typename typetraits<T>::unsigned_type     unsigned_type;
00062       typedef self                                      cumul_type;
00063       typedef self                                      largest_type;
00064       typedef self                                      signed_largest_type;
00065       typedef self                                      signed_cumul_type;
00066       typedef self                                      unsigned_largest_type;
00067       typedef self                                      unsigned_cumul_type;
00068       typedef typename typetraits<T>::integer_type      integer_type;
00069     };
00070 
00071   } // end of internal.
00072 
00073   /*-------------------.
00074   | cycle<T, interval> |
00075   `-------------------*/
00076 
00077   template <class T,
00078             class interval>
00079   class cycle : 
00080     public type_traits<T>::template build_value_type<cycle<T, interval> >::ret
00081   {
00082   public:
00083     typedef cycle<T, interval> self;
00084 
00085   private:
00086     typedef ntgi_optraits_type(self)            optraits_type;
00087     typedef ntg_base_type(self)                 base_type;
00088     typedef ntgi_storage_type(base_type)        base_storage_type;
00089 
00090   public:
00091     cycle () { this->val_ = 0; }
00092 
00093     template <class U>
00094     cycle (const U& u)
00095     {
00096       ntg_is_a(U, real)::ensure();
00097       this->val_ = optraits_type::check(u);
00098     }
00099     template <class U>
00100     self&
00101     operator=(const U& u)
00102     {
00103       this->val_ = optraits_type::check(u);
00104       return *this;
00105     }
00106 
00107     operator base_storage_type() const { return this->val_; }
00108   };
00109 
00110   template<class T, class interval>
00111   inline std::ostream&
00112   operator<<(std::ostream& stream, const cycle<T, interval>& rhs)
00113   {
00114     // FIXME: cast needed for cycle<unsigned char, ...>.
00115     stream << (ntg_largest_type(T))(rhs.val());
00116     return stream;
00117   }
00118 
00119   namespace internal {
00120 
00121     /*----------------.
00122     | optraits<cycle> |
00123     `----------------*/
00124 
00125     template<class T,
00126              class interval>
00127     struct optraits<cycle<T, interval> > : public optraits<T>
00128     {
00129     public:
00130       typedef cycle<T, interval> self;
00131     
00132     private:
00133       typedef typename typetraits<self>::storage_type   storage_type_;
00134       typedef typename interval::storage_type           interval_type_;
00135       typedef typename typetraits<self>::behavior_type  behavior_type_;
00136 
00137     public:
00138       static interval_type_ min()
00139       { return interval::min(); }
00140 
00141       static interval_type_ max()
00142       { return interval::max(); }
00143 
00144       static interval_type_ inf()
00145       { return interval::inf(); }
00146 
00147       static interval_type_ sup()
00148       { return interval::sup(); }
00149 
00150       template <class P>
00151       static storage_type_
00152       check(const P& rhs)
00153       { return behavior_type_::check(rhs); }
00154 
00155       static std::string
00156       name()
00157       {
00158         std::ostringstream out;
00159         out << "cycle<" << optraits<T>::name() << ", " 
00160             << interval::name() << ">"<< std::ends;
00161         return out.str();
00162       }
00163     };
00164 
00165     // Inherit operator traits from the base type.
00166     template <class Op, class T, class I, class U>
00167     struct operator_traits<Op, cycle<T, I>, U> 
00168       : public deduce_from_traits<Op, T, U>::deduced_traits
00169     {}; 
00170 
00171     // Inherit operator traits from the base type.
00172     template <class Op, class T, class I, class U>
00173     struct operator_traits<Op, U, cycle<T, I> >
00174       : public deduce_from_traits<Op, U, T>::deduced_traits
00175     {};
00176 
00177     // Inherit operator traits from the base type.
00178     template <class Op, class T1, class I1, class T2, class I2>
00179     struct operator_traits<Op, cycle<T1, I1>, cycle<T2, I2> >
00180       : public deduce_from_traits<Op, T1, T2>::deduced_traits
00181     {};
00182 
00183   } // end of internal.
00184 
00185 } // end of ntg.
00186 
00187 #endif // !NTG_REAL_CYCLE_HH

Generated on Thu Apr 15 20:13:07 2004 for Olena by doxygen 1.3.6-20040222