00001 # if !defined(TS_NUMERIC_TYPE_HEADER)
00002 # define TS_NUMERIC_TYPE_HEADER
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00014 
00015 
00016 
00017 
00018 
00019 
00020 
00021 
00022 
00023 
00024 
00025 
00026 
00027 
00028 
00029 
00030 
00031 
00032 
00033 
00034 
00035 
00036 
00037 
00038 
00039 
00040 
00041 
00042 
00043 
00044 # include <limits>
00045 
00046 namespace ts {
00047 
00048 
00049 template < typename T, typename X > class NumericType;
00050 
00051 
00052 
00053 
00054 
00055 
00056 
00057 
00058 
00059 
00060 
00061 
00062 
00063 
00064 
00065 
00066 
00067 
00068 template <
00069   typename T, 
00070   typename X 
00071 > class NumericTypeIntOperators {
00072 public:
00073     NumericType<T,X>& operator += ( int t );
00074     NumericType<T,X>& operator -= ( int t );
00075 
00076     
00077     NumericType<T,X> operator +  ( int t );
00078     NumericType<T,X> operator -  ( int t );
00079     NumericType<T,X> operator +  ( int t ) const;
00080     NumericType<T,X> operator -  ( int t ) const;
00081 };
00082 
00083 template < typename T, typename X > NumericType<T,X>
00084 operator + ( int t, NumericTypeIntOperators<T,X> const& );
00085 
00086 template < typename T, typename X > NumericType<T,X>
00087 operator - ( int t, NumericTypeIntOperators<T,X> const& );
00088 
00089 
00090 
00091 
00092 
00093 
00094 
00095 
00096 template <
00097   typename T, 
00098   typename X 
00099 > class NumericType : public NumericTypeIntOperators<T,X> {
00100 public:
00101     typedef T raw_type; 
00102     typedef NumericType self; 
00103 
00104 
00105     
00106     using NumericTypeIntOperators<T,X>::operator +=;
00107     using NumericTypeIntOperators<T,X>::operator -=;
00108     using NumericTypeIntOperators<T,X>::operator +;
00109     using NumericTypeIntOperators<T,X>::operator -;
00110 
00111 
00112 
00113     NumericType();
00114 
00115     NumericType(
00116       raw_type const t 
00117     );
00118 
00119     NumericType & operator = (raw_type const t);
00120 
00121     NumericType & operator = (self const& that);
00122 
00123 
00124 
00125 
00126 
00127     operator raw_type const& () const { return _t; }
00128 
00129     operator raw_type& () { return _t; }
00130 
00131     raw_type raw() const { return _t; }
00132 
00133     
00134     self& operator += ( self const& that );
00135     self& operator -= ( self const& that );
00136 
00137     self& operator += ( raw_type t );
00138     self& operator -= ( raw_type t );
00139 
00140     self operator +  ( self const& that );
00141     self operator -  ( self const& that );
00142 
00143     self operator +  ( raw_type t );
00144     self operator -  ( raw_type t );
00145 
00146     self& operator ++();
00147     self operator ++(int);
00148     self& operator --();
00149     self operator --(int);
00150 
00151 private:
00152     raw_type   _t;
00153 };
00154 
00155 
00156 template < typename T, typename X > NumericType<T,X>::NumericType() { }
00157 template < typename T, typename X > NumericType<T,X>::NumericType(raw_type const t) : _t(t) { }
00158 template < typename T, typename X > NumericType<T,X>& NumericType<T,X>::operator = (raw_type const t) { _t = t; return *this; }
00159 template < typename T, typename X > NumericType<T,X>& NumericType<T,X>::operator = (self const& that) { _t = that._t; return *this; }
00160 
00161 template < typename T, typename X > NumericType<T,X>& NumericType<T,X>::operator += ( self const& that ) { _t += that._t; return *this; }
00162 template < typename T, typename X > NumericType<T,X>& NumericType<T,X>::operator -= ( self const& that ) { _t -= that._t; return *this; }
00163 template < typename T, typename X > NumericType<T,X> NumericType<T,X>::operator +  ( self const& that ) { return self(_t + that._t); }
00164 template < typename T, typename X > NumericType<T,X> NumericType<T,X>::operator -  ( self const& that ) { return self(_t - that._t); }
00165 
00166 template < typename T, typename X > NumericType<T,X>& NumericType<T,X>::operator += ( raw_type t ) { _t += t; return *this; }
00167 template < typename T, typename X > NumericType<T,X>& NumericType<T,X>::operator -= ( raw_type t ) { _t -= t; return *this; }
00168 template < typename T, typename X > NumericType<T,X> NumericType<T,X>::operator +  ( raw_type t ) { return self(_t + t); }
00169 template < typename T, typename X > NumericType<T,X> NumericType<T,X>::operator -  ( raw_type t ) { return self(_t - t); }
00170 
00171 template < typename T, typename X > NumericType<T,X>& NumericType<T,X>::operator ++() { ++_t; return *this; }
00172 template < typename T, typename X > NumericType<T,X>& NumericType<T,X>::operator --() { --_t; return *this; }
00173 template < typename T, typename X > NumericType<T,X> NumericType<T,X>::operator ++(int) { self tmp(*this); ++_t; return tmp; }
00174 template < typename T, typename X > NumericType<T,X> NumericType<T,X>::operator --(int) { self tmp(*this); --_t; return tmp; }
00175 
00176 template < typename T, typename X > NumericType<T,X> operator +  ( T const& lhs, NumericType<T,X> const& rhs ) { return rhs + lhs; }
00177 template < typename T, typename X > NumericType<T,X> operator -  ( T const& lhs, NumericType<T,X> const& rhs ) { return NumericType<T,X>(lhs - rhs.raw()); }
00178 
00179 
00180 } 
00181 
00182 # endif // TS_NUMERIC_TYPE_HEADER