Milena (Olena)
User documentation 2.0a Id
|
00001 // Copyright (C) 2006, 2007, 2008, 2009 EPITA Research and Development Laboratory (LRDE) 00002 // 00003 // This file is part of Olena. 00004 // 00005 // Olena is free software: you can redistribute it and/or modify it under 00006 // the terms of the GNU General Public License as published by the Free 00007 // Software Foundation, version 2 of the License. 00008 // 00009 // Olena is distributed in the hope that it will be useful, 00010 // but WITHOUT ANY WARRANTY; without even the implied warranty of 00011 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00012 // General Public License for more details. 00013 // 00014 // You should have received a copy of the GNU General Public License 00015 // along with Olena. If not, see <http://www.gnu.org/licenses/>. 00016 // 00017 // As a special exception, you may use this file as part of a free 00018 // software project without restriction. Specifically, if other files 00019 // instantiate templates or use macros or inline functions from this 00020 // file, or you compile this file and link it with other files to produce 00021 // an executable, this file does not by itself cause the resulting 00022 // executable to be covered by the GNU General Public License. This 00023 // exception does not however invalidate any other reasons why the 00024 // executable file might be covered by the GNU General Public License. 00025 00026 #ifndef MLN_VALUE_FLOAT01__HH 00027 # define MLN_VALUE_FLOAT01__HH 00028 00034 # include <iostream> 00035 # include <mln/core/contract.hh> 00036 # include <mln/metal/math/pow.hh> 00037 # include <mln/metal/bexpr.hh> 00038 00039 # include <mln/value/int_u.hh> 00040 # include <mln/value/concept/floating.hh> 00041 # include <mln/value/internal/convert.hh> 00042 # include <mln/value/float01.hh> 00043 # include <mln/trait/value_.hh> 00044 00045 00046 00047 namespace mln 00048 { 00049 00050 // Fwd decls. 00051 namespace value { 00052 class float01; 00053 template <unsigned n> struct float01_; 00054 } 00055 00056 00057 namespace trait 00058 { 00059 00060 template <unsigned n> 00061 struct value_< mln::value::float01_<n> > 00062 { 00063 enum constants_ { 00064 dim = 1, 00065 nbits = n, 00066 card = mln_value_card_from_(nbits) 00067 }; 00068 00069 typedef trait::value::nature::floating nature; 00070 typedef trait::value::kind::data kind; 00071 typedef mln_value_quant_from_(card) quant; 00072 00073 static float min() { return 0.f; } 00074 static float max() { return 1.f; } 00075 static float epsilon() { return 0.f; } 00076 00077 typedef float comp; 00078 00079 typedef float sum; 00080 }; 00081 00082 } // end of namespace trait 00083 00084 00085 namespace value 00086 { 00087 00089 template <unsigned n> 00090 struct float01_ 00091 00092 : public Floating< float01_<n> >, 00093 00094 public internal::value_like_< float, // Equivalent. // FIXME: Why not float01? 00095 mln_enc(int_u<n>), // Encoding. 00096 float, // Interoperation. 00097 float01_<n> > // Exact. 00098 { 00100 float01_(); 00101 00103 float01_(float val); 00104 00106 float01_(const mln::literal::zero_t&); 00107 float01_& operator=(const mln::literal::zero_t&); 00108 float01_(const mln::literal::one_t&); 00109 float01_& operator=(const mln::literal::one_t&); 00111 00113 float01_<n>& operator=(float val); 00114 00116 float value() const; 00117 00119 void set_ind(unsigned long val); 00120 00122 operator float() const; 00123 00124 private: 00125 typedef mln_enc(int_u<n>) enc_; 00126 }; 00127 00128 00129 namespace internal 00130 { 00131 00132 template <unsigned n> 00133 struct convert_< float01_<n> > 00134 { 00135 static float01_<n> value_at_index(unsigned i) 00136 { 00137 float01_<n> tmp; 00138 tmp.set_ind(i); 00139 return tmp; 00140 } 00141 00142 static unsigned index_of_value(const float01_<n>& v) 00143 { 00144 return v.to_enc(); 00145 } 00146 }; 00147 } 00148 00149 00151 template <unsigned n> 00152 std::ostream& operator<<(std::ostream& ostr, const float01_<n>& f); 00153 00154 00155 template <unsigned n, unsigned m> 00156 bool approx_equal(const float01_<n>& lhs, const float01_<m>& rhs); 00157 00158 template <unsigned n> 00159 bool approx_equal(const float01_<n>& lhs, const float f); 00160 00161 00162 00163 # ifndef MLN_INCLUDE_ONLY 00164 00165 // Float01_<n>. 00166 00167 template <unsigned n> 00168 inline 00169 float01_<n>::float01_() 00170 { 00171 } 00172 00173 template <unsigned n> 00174 inline 00175 float01_<n>::float01_(float val) 00176 { 00177 mln_precondition(val >= 0.f); 00178 mln_precondition(val <= 1.f); 00179 this->v_ = static_cast<enc_>(val * (float(mln_max(enc_)) - 1.f)); // FIXME 00180 } 00181 00182 template <unsigned n> 00183 inline 00184 float 00185 float01_<n>::value() const 00186 { 00187 return float(this->v_) / (float(mln_max(enc_)) - 1.f); // FIXME 00188 } 00189 00190 template <unsigned n> 00191 inline 00192 void 00193 float01_<n>::set_ind(unsigned long val) 00194 { 00195 this->v_ = static_cast<enc_>(val); 00196 } 00197 00198 template <unsigned n> 00199 inline 00200 float01_<n>::float01_(const mln::literal::zero_t&) 00201 { 00202 this->v_ = 0; 00203 } 00204 00205 template <unsigned n> 00206 inline 00207 float01_<n>& 00208 float01_<n>::operator=(const mln::literal::zero_t&) 00209 { 00210 this->v_ = 0; 00211 return *this; 00212 } 00213 00214 template <unsigned n> 00215 inline 00216 float01_<n>::float01_(const mln::literal::one_t&) 00217 { 00218 this->v_ = 1; 00219 } 00220 00221 template <unsigned n> 00222 inline 00223 float01_<n>& 00224 float01_<n>::operator=(const mln::literal::one_t&) 00225 { 00226 this->v_ = 1; 00227 return *this; 00228 } 00229 00230 template <unsigned n> 00231 inline 00232 float01_<n>& 00233 float01_<n>::operator=(float val) 00234 { 00235 mln_precondition(val >= 0.f); 00236 mln_precondition(val <= 1.f); 00237 this->v_ = static_cast<enc_>(val * (float(mln_max(enc_)) - 1.f)); // FIXME 00238 return *this; 00239 } 00240 00241 template <unsigned n> 00242 inline 00243 float01_<n>::operator float() const 00244 { 00245 return float(this->v_) / (float(mln_max(enc_)) - 1.f); 00246 } 00247 00248 00249 // Operators. 00250 00251 template <unsigned n> 00252 inline 00253 std::ostream& operator<<(std::ostream& ostr, const float01_<n>& f) 00254 { 00255 return ostr << f.value(); 00256 } 00257 00258 template <unsigned n, unsigned m> 00259 inline 00260 bool approx_equal(const float01_<n>& lhs, const float01_<m>& rhs) 00261 { 00262 return float01(lhs) == float01(rhs); 00263 } 00264 00265 template <unsigned n> 00266 inline 00267 bool approx_equal(const float01_<n>& lhs, float f) 00268 { 00269 return float01(lhs) == float01_<n>(f); 00270 } 00271 00272 00273 # endif // ! MLN_INCLUDE_ONLY 00274 00275 } // end of namespace mln::value 00276 00277 } // end of namespace mln 00278 00279 #endif // ! MLN_VALUE_FLOAT01__HH