// (C) Copyright John Maddock 2014. // Use, modification and distribution are subject to the // Boost Software License, Version 1.0. (See accompanying file // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) #ifndef BOOST_MATH_TOOLS_MP_T #define BOOST_MATH_TOOLS_MP_T #ifndef BOOST_MATH_PRECISION #define BOOST_MATH_PRECISION 1000 #endif #if defined(BOOST_MATH_USE_MPFR) #include typedef boost::multiprecision::number > mp_t; #else #include typedef boost::multiprecision::number > mp_t; #endif inline mp_t ConvPrec(mp_t arg, int digits) { int e1, e2; mp_t t = frexp(arg, &e1); t = frexp(floor(ldexp(t, digits + 1)), &e2); return ldexp(t, e1); } inline mp_t relative_error(mp_t a, mp_t b) { mp_t min_val = boost::math::tools::min_value(); mp_t max_val = boost::math::tools::max_value(); if((a != 0) && (b != 0)) { // mp_tODO: use isfinite: if(fabs(b) >= max_val) { if(fabs(a) >= max_val) return 0; // one infinity is as good as another! } // If the result is denormalised, treat all denorms as equivalent: if((a < min_val) && (a > 0)) a = min_val; else if((a > -min_val) && (a < 0)) a = -min_val; if((b < min_val) && (b > 0)) b = min_val; else if((b > -min_val) && (b < 0)) b = -min_val; return (std::max)(fabs((a - b) / a), fabs((a - b) / b)); } // Handle special case where one or both are zero: if(min_val == 0) return fabs(a - b); if(fabs(a) < min_val) a = min_val; if(fabs(b) < min_val) b = min_val; return (std::max)(fabs((a - b) / a), fabs((a - b) / b)); } #endif // BOOST_MATH_TOOLS_MP_T