1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/lemon/tolerance.h Thu Aug 10 14:56:36 2006 +0000
1.3 @@ -0,0 +1,387 @@
1.4 +/* -*- C++ -*-
1.5 + *
1.6 + * This file is a part of LEMON, a generic C++ optimization library
1.7 + *
1.8 + * Copyright (C) 2003-2006
1.9 + * Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
1.10 + * (Egervary Research Group on Combinatorial Optimization, EGRES).
1.11 + *
1.12 + * Permission to use, modify and distribute this software is granted
1.13 + * provided that this copyright notice appears in all copies. For
1.14 + * precise terms see the accompanying LICENSE file.
1.15 + *
1.16 + * This software is provided "AS IS" with no warranty of any kind,
1.17 + * express or implied, and with no claim as to its suitability for any
1.18 + * purpose.
1.19 + *
1.20 + */
1.21 +
1.22 +#ifndef LEMON_TOLERANCE_H
1.23 +#define LEMON_TOLERANCE_H
1.24 +
1.25 +///\ingroup misc
1.26 +///\file
1.27 +///\brief A basic tool to handle the anomalies of calculation with
1.28 +///floating point numbers.
1.29 +///
1.30 +///\todo It should be in a module like "Basic tools"
1.31 +
1.32 +
1.33 +namespace lemon {
1.34 +
1.35 + /// \addtogroup misc
1.36 + /// @{
1.37 +
1.38 + ///\brief A class to provide a basic way to
1.39 + ///handle the comparison of numbers that are obtained
1.40 + ///as a result of a probably inexact computation.
1.41 + ///
1.42 + ///Tolerance is a class to provide a basic way to
1.43 + ///handle the comparison of numbers that are obtained
1.44 + ///as a result of a probably inexact computation.
1.45 + ///
1.46 + ///This is an abstract class, it should be specialized for all numerical
1.47 + ///data types. These specialized classes like \ref Tolerance\<double\>
1.48 + ///may offer additional tuning parameters.
1.49 + ///
1.50 + ///\sa Tolerance<float>
1.51 + ///\sa Tolerance<double>
1.52 + ///\sa Tolerance<long double>
1.53 + ///\sa Tolerance<int>
1.54 + ///\sa Tolerance<long long int>
1.55 + ///\sa Tolerance<unsigned int>
1.56 + ///\sa Tolerance<unsigned long long int>
1.57 +
1.58 + template<class T>
1.59 + class Tolerance
1.60 + {
1.61 + public:
1.62 + typedef T Value;
1.63 +
1.64 + ///\name Comparisons
1.65 + ///The concept is that these bool functions return with \c true only if
1.66 + ///the related comparisons hold even if some numerical error appeared
1.67 + ///during the computations.
1.68 +
1.69 + ///@{
1.70 +
1.71 + ///Returns \c true if \c a is \e surely strictly less than \c b
1.72 + static bool less(Value a,Value b) {return false;}
1.73 + ///Returns \c true if \c a is \e surely different from \c b
1.74 + static bool different(Value a,Value b) {return false;}
1.75 + ///Returns \c true if \c a is \e surely positive
1.76 + static bool positive(Value a) {return false;}
1.77 + ///Returns \c true if \c a is \e surely negative
1.78 + static bool negative(Value a) {return false;}
1.79 + ///Returns \c true if \c a is \e surely non-zero
1.80 + static bool nonZero(Value a) {return false;}
1.81 +
1.82 + ///@}
1.83 +
1.84 + ///Returns the zero value.
1.85 + static Value zero() {return T();}
1.86 +
1.87 + // static bool finite(Value a) {}
1.88 + // static Value big() {}
1.89 + // static Value negativeBig() {}
1.90 + };
1.91 +
1.92 +
1.93 + ///Float specialization of \ref Tolerance.
1.94 +
1.95 + ///Float specialization of \ref Tolerance.
1.96 + ///\sa Tolerance
1.97 + ///\relates Tolerance
1.98 + template<>
1.99 + class Tolerance<float>
1.100 + {
1.101 + static float def_epsilon;
1.102 + float _epsilon;
1.103 + public:
1.104 + ///\e
1.105 + typedef float Value;
1.106 +
1.107 + ///Constructor setting the epsilon tolerance to the default value.
1.108 + Tolerance() : _epsilon(def_epsilon) {}
1.109 + ///Constructor setting the epsilon tolerance.
1.110 + Tolerance(float e) : _epsilon(e) {}
1.111 +
1.112 + ///Return the epsilon value.
1.113 + Value epsilon() const {return _epsilon;}
1.114 + ///Set the epsilon value.
1.115 + void epsilon(Value e) {_epsilon=e;}
1.116 +
1.117 + ///Return the default epsilon value.
1.118 + static Value defaultEpsilon() {return def_epsilon;}
1.119 + ///Set the default epsilon value.
1.120 + static void defaultEpsilon(Value e) {def_epsilon=e;}
1.121 +
1.122 + ///\name Comparisons
1.123 + ///See class Tolerance for more details.
1.124 +
1.125 + ///@{
1.126 +
1.127 + ///Returns \c true if \c a is \e surely strictly less than \c b
1.128 + bool less(Value a,Value b) const {return a+_epsilon<b;}
1.129 + ///Returns \c true if \c a is \e surely different from \c b
1.130 + bool different(Value a,Value b) const { return less(a,b)||less(b,a); }
1.131 + ///Returns \c true if \c a is \e surely positive
1.132 + bool positive(Value a) const { return _epsilon<a; }
1.133 + ///Returns \c true if \c a is \e surely negative
1.134 + bool negative(Value a) const { return -_epsilon>a; }
1.135 + ///Returns \c true if \c a is \e surely non-zero
1.136 + bool nonZero(Value a) const { return positive(a)||negative(a); };
1.137 +
1.138 + ///@}
1.139 +
1.140 + ///Returns zero
1.141 + static Value zero() {return 0;}
1.142 + };
1.143 +
1.144 + ///Double specialization of \ref Tolerance.
1.145 +
1.146 + ///Double specialization of \ref Tolerance.
1.147 + ///\sa Tolerance
1.148 + ///\relates Tolerance
1.149 + template<>
1.150 + class Tolerance<double>
1.151 + {
1.152 + static double def_epsilon;
1.153 + double _epsilon;
1.154 + public:
1.155 + ///\e
1.156 + typedef double Value;
1.157 +
1.158 + ///Constructor setting the epsilon tolerance to the default value.
1.159 + Tolerance() : _epsilon(def_epsilon) {}
1.160 + ///Constructor setting the epsilon tolerance.
1.161 + Tolerance(double e) : _epsilon(e) {}
1.162 +
1.163 + ///Return the epsilon value.
1.164 + Value epsilon() const {return _epsilon;}
1.165 + ///Set the epsilon value.
1.166 + void epsilon(Value e) {_epsilon=e;}
1.167 +
1.168 + ///Return the default epsilon value.
1.169 + static Value defaultEpsilon() {return def_epsilon;}
1.170 + ///Set the default epsilon value.
1.171 + static void defaultEpsilon(Value e) {def_epsilon=e;}
1.172 +
1.173 + ///\name Comparisons
1.174 + ///See class Tolerance for more details.
1.175 +
1.176 + ///@{
1.177 +
1.178 + ///Returns \c true if \c a is \e surely strictly less than \c b
1.179 + bool less(Value a,Value b) const {return a+_epsilon<b;}
1.180 + ///Returns \c true if \c a is \e surely different from \c b
1.181 + bool different(Value a,Value b) const { return less(a,b)||less(b,a); }
1.182 + ///Returns \c true if \c a is \e surely positive
1.183 + bool positive(Value a) const { return _epsilon<a; }
1.184 + ///Returns \c true if \c a is \e surely negative
1.185 + bool negative(Value a) const { return -_epsilon>a; }
1.186 + ///Returns \c true if \c a is \e surely non-zero
1.187 + bool nonZero(Value a) const { return positive(a)||negative(a); };
1.188 +
1.189 + ///@}
1.190 +
1.191 + ///Returns zero
1.192 + static Value zero() {return 0;}
1.193 + };
1.194 +
1.195 + ///Long double specialization of \ref Tolerance.
1.196 +
1.197 + ///Long double specialization of \ref Tolerance.
1.198 + ///\sa Tolerance
1.199 + ///\relates Tolerance
1.200 + template<>
1.201 + class Tolerance<long double>
1.202 + {
1.203 + static long double def_epsilon;
1.204 + long double _epsilon;
1.205 + public:
1.206 + ///\e
1.207 + typedef long double Value;
1.208 +
1.209 + ///Constructor setting the epsilon tolerance to the default value.
1.210 + Tolerance() : _epsilon(def_epsilon) {}
1.211 + ///Constructor setting the epsilon tolerance.
1.212 + Tolerance(long double e) : _epsilon(e) {}
1.213 +
1.214 + ///Return the epsilon value.
1.215 + Value epsilon() const {return _epsilon;}
1.216 + ///Set the epsilon value.
1.217 + void epsilon(Value e) {_epsilon=e;}
1.218 +
1.219 + ///Return the default epsilon value.
1.220 + static Value defaultEpsilon() {return def_epsilon;}
1.221 + ///Set the default epsilon value.
1.222 + static void defaultEpsilon(Value e) {def_epsilon=e;}
1.223 +
1.224 + ///\name Comparisons
1.225 + ///See class Tolerance for more details.
1.226 +
1.227 + ///@{
1.228 +
1.229 + ///Returns \c true if \c a is \e surely strictly less than \c b
1.230 + bool less(Value a,Value b) const {return a+_epsilon<b;}
1.231 + ///Returns \c true if \c a is \e surely different from \c b
1.232 + bool different(Value a,Value b) const { return less(a,b)||less(b,a); }
1.233 + ///Returns \c true if \c a is \e surely positive
1.234 + bool positive(Value a) const { return _epsilon<a; }
1.235 + ///Returns \c true if \c a is \e surely negative
1.236 + bool negative(Value a) const { return -_epsilon>a; }
1.237 + ///Returns \c true if \c a is \e surely non-zero
1.238 + bool nonZero(Value a) const { return positive(a)||negative(a); };
1.239 +
1.240 + ///@}
1.241 +
1.242 + ///Returns zero
1.243 + static Value zero() {return 0;}
1.244 + };
1.245 +
1.246 + ///Integer specialization of \ref Tolerance.
1.247 +
1.248 + ///Integer specialization of \ref Tolerance.
1.249 + ///\sa Tolerance
1.250 + template<>
1.251 + class Tolerance<int>
1.252 + {
1.253 + public:
1.254 + ///\e
1.255 + typedef int Value;
1.256 +
1.257 + ///\name Comparisons
1.258 + ///See \ref Tolerance for more details.
1.259 +
1.260 + ///@{
1.261 +
1.262 + ///Returns \c true if \c a is \e surely strictly less than \c b
1.263 + static bool less(Value a,Value b) { return a<b;}
1.264 + ///Returns \c true if \c a is \e surely different from \c b
1.265 + static bool different(Value a,Value b) { return a!=b; }
1.266 + ///Returns \c true if \c a is \e surely positive
1.267 + static bool positive(Value a) { return 0<a; }
1.268 + ///Returns \c true if \c a is \e surely negative
1.269 + static bool negative(Value a) { return 0>a; }
1.270 + ///Returns \c true if \c a is \e surely non-zero
1.271 + static bool nonZero(Value a) { return a!=0; };
1.272 +
1.273 + ///@}
1.274 +
1.275 + ///Returns zero
1.276 + static Value zero() {return 0;}
1.277 + };
1.278 +
1.279 + ///Unsigned integer specialization of \ref Tolerance.
1.280 +
1.281 + ///Unsigned integer specialization of \ref Tolerance.
1.282 + ///\sa Tolerance
1.283 + template<>
1.284 + class Tolerance<unsigned int>
1.285 + {
1.286 + public:
1.287 + ///\e
1.288 + typedef unsigned int Value;
1.289 +
1.290 + ///\name Comparisons
1.291 + ///See \ref Tolerance for more details.
1.292 +
1.293 + ///@{
1.294 +
1.295 + ///Returns \c true if \c a is \e surely strictly less than \c b
1.296 + static bool less(Value a,Value b) { return a<b;}
1.297 + ///Returns \c true if \c a is \e surely different from \c b
1.298 + static bool different(Value a,Value b) { return a!=b; }
1.299 + ///Returns \c true if \c a is \e surely positive
1.300 + static bool positive(Value a) { return 0<a; }
1.301 + ///Returns \c true if \c a is \e surely negative
1.302 + static bool negative(Value) { return false; }
1.303 + ///Returns \c true if \c a is \e surely non-zero
1.304 + static bool nonZero(Value a) { return a!=0; };
1.305 +
1.306 + ///@}
1.307 +
1.308 + ///Returns zero
1.309 + static Value zero() {return 0;}
1.310 + };
1.311 +
1.312 +#ifndef __STRICT_ANSI__
1.313 +
1.314 + ///Long long integer specialization of \ref Tolerance.
1.315 +
1.316 + ///Long long integer specialization of \ref Tolerance.
1.317 + ///\warning This class (more exactly, type <tt>long long</tt>)
1.318 + ///is not ansi compatible.
1.319 + ///\sa Tolerance
1.320 + template<>
1.321 + class Tolerance<long long int>
1.322 + {
1.323 + public:
1.324 + ///\e
1.325 + typedef long long int Value;
1.326 +
1.327 + ///\name Comparisons
1.328 + ///See \ref Tolerance for more details.
1.329 +
1.330 + ///@{
1.331 +
1.332 + ///Returns \c true if \c a is \e surely strictly less than \c b
1.333 + static bool less(Value a,Value b) { return a<b;}
1.334 + ///Returns \c true if \c a is \e surely different from \c b
1.335 + static bool different(Value a,Value b) { return a!=b; }
1.336 + ///Returns \c true if \c a is \e surely positive
1.337 + static bool positive(Value a) { return 0<a; }
1.338 + ///Returns \c true if \c a is \e surely negative
1.339 + static bool negative(Value a) { return 0>a; }
1.340 + ///Returns \c true if \c a is \e surely non-zero
1.341 + static bool nonZero(Value a) { return a!=0;};
1.342 +
1.343 + ///@}
1.344 +
1.345 + ///Returns zero
1.346 + static Value zero() {return 0;}
1.347 + };
1.348 +
1.349 + ///Unsigned long long integer specialization of \ref Tolerance.
1.350 +
1.351 + ///Unsigned long long integer specialization of \ref Tolerance.
1.352 + ///\warning This class (more exactly, type <tt>unsigned long long</tt>)
1.353 + ///is not ansi compatible.
1.354 + ///\sa Tolerance
1.355 + template<>
1.356 + class Tolerance<unsigned long long int>
1.357 + {
1.358 + public:
1.359 + ///\e
1.360 + typedef unsigned long long int Value;
1.361 +
1.362 + ///\name Comparisons
1.363 + ///See \ref Tolerance for more details.
1.364 +
1.365 + ///@{
1.366 +
1.367 + ///Returns \c true if \c a is \e surely strictly less than \c b
1.368 + static bool less(Value a,Value b) { return a<b;}
1.369 + ///Returns \c true if \c a is \e surely different from \c b
1.370 + static bool different(Value a,Value b) { return a!=b; }
1.371 + ///Returns \c true if \c a is \e surely positive
1.372 + static bool positive(Value a) { return 0<a; }
1.373 + ///Returns \c true if \c a is \e surely negative
1.374 + static bool negative(Value) { return false; }
1.375 + ///Returns \c true if \c a is \e surely non-zero
1.376 + static bool nonZero(Value a) { return a!=0;};
1.377 +
1.378 + ///@}
1.379 +
1.380 + ///Returns zero
1.381 + static Value zero() {return 0;}
1.382 + };
1.383 +
1.384 +#endif
1.385 +
1.386 + /// @}
1.387 +
1.388 +} //namespace lemon
1.389 +
1.390 +#endif //LEMON_TOLERANCE_H