float128.hpp 23 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649
  1. ///////////////////////////////////////////////////////////////
  2. // Copyright 2013 John Maddock. Distributed under the Boost
  3. // Software License, Version 1.0. (See accompanying file
  4. // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_
  5. #ifndef BOOST_MP_FLOAT128_HPP
  6. #define BOOST_MP_FLOAT128_HPP
  7. #include <boost/config.hpp>
  8. #include <boost/scoped_array.hpp>
  9. #include <boost/multiprecision/number.hpp>
  10. #if defined(BOOST_INTEL) && !defined(BOOST_MP_USE_FLOAT128) && !defined(BOOST_MP_USE_QUAD)
  11. # if defined(BOOST_INTEL_CXX_VERSION) && (BOOST_INTEL_CXX_VERSION >= 1310) && defined(__GNUC__)
  12. # if (__GNUC__ > 4) || ((__GNUC__ == 4) && (__GNUC_MINOR__ >= 6))
  13. # define BOOST_MP_USE_FLOAT128
  14. # endif
  15. # endif
  16. # ifndef BOOST_MP_USE_FLOAT128
  17. # define BOOST_MP_USE_QUAD
  18. # endif
  19. #endif
  20. #if defined(__GNUC__) && !defined(BOOST_MP_USE_FLOAT128) && !defined(BOOST_MP_USE_QUAD)
  21. # define BOOST_MP_USE_FLOAT128
  22. #endif
  23. #if !defined(BOOST_MP_USE_FLOAT128) && !defined(BOOST_MP_USE_QUAD)
  24. # error "Sorry compiler is neither GCC, not Intel, don't know how to configure this header."
  25. #endif
  26. #if defined(BOOST_MP_USE_FLOAT128) && defined(BOOST_MP_USE_QUAD)
  27. # error "Oh dear, both BOOST_MP_USE_FLOAT128 and BOOST_MP_USE_QUAD are defined, which one should I be using?"
  28. #endif
  29. #if defined(BOOST_MP_USE_FLOAT128)
  30. extern "C" {
  31. #include <quadmath.h>
  32. }
  33. typedef __float128 float128_type;
  34. #elif defined(BOOST_MP_USE_QUAD)
  35. #include <boost/multiprecision/detail/float_string_cvt.hpp>
  36. typedef _Quad float128_type;
  37. extern "C" {
  38. _Quad __ldexpq(_Quad, int);
  39. _Quad __frexpq(_Quad, int*);
  40. _Quad __fabsq(_Quad);
  41. _Quad __floorq(_Quad);
  42. _Quad __ceilq(_Quad);
  43. _Quad __sqrtq(_Quad);
  44. _Quad __truncq(_Quad);
  45. _Quad __expq(_Quad);
  46. _Quad __powq(_Quad, _Quad);
  47. _Quad __logq(_Quad);
  48. _Quad __log10q(_Quad);
  49. _Quad __sinq(_Quad);
  50. _Quad __cosq(_Quad);
  51. _Quad __tanq(_Quad);
  52. _Quad __asinq(_Quad);
  53. _Quad __acosq(_Quad);
  54. _Quad __atanq(_Quad);
  55. _Quad __sinhq(_Quad);
  56. _Quad __coshq(_Quad);
  57. _Quad __tanhq(_Quad);
  58. _Quad __fmodq(_Quad, _Quad);
  59. _Quad __atan2q(_Quad, _Quad);
  60. #define ldexpq __ldexpq
  61. #define frexpq __frexpq
  62. #define fabsq __fabsq
  63. #define floorq __floorq
  64. #define ceilq __ceilq
  65. #define sqrtq __sqrtq
  66. #define truncq __truncq
  67. #define expq __expq
  68. #define powq __powq
  69. #define logq __logq
  70. #define log10q __log10q
  71. #define sinq __sinq
  72. #define cosq __cosq
  73. #define tanq __tanq
  74. #define asinq __asinq
  75. #define acosq __acosq
  76. #define atanq __atanq
  77. #define sinhq __sinhq
  78. #define coshq __coshq
  79. #define tanhq __tanhq
  80. #define fmodq __fmodq
  81. #define atan2q __atan2q
  82. }
  83. inline _Quad isnanq(_Quad v)
  84. {
  85. return v != v;
  86. }
  87. inline _Quad isinfq(_Quad v)
  88. {
  89. return __fabsq(v) > 1.18973149535723176508575932662800702e4932Q;
  90. }
  91. #endif
  92. namespace boost{
  93. namespace multiprecision{
  94. namespace backends{
  95. struct float128_backend;
  96. }
  97. using backends::float128_backend;
  98. template<>
  99. struct number_category<backends::float128_backend> : public mpl::int_<number_kind_floating_point> {};
  100. template<>
  101. struct number_category<float128_type> : public mpl::int_<number_kind_floating_point> {};
  102. typedef number<float128_backend, et_off> float128;
  103. namespace backends{
  104. struct float128_backend
  105. {
  106. typedef mpl::list<signed char, short, int, long, boost::long_long_type> signed_types;
  107. typedef mpl::list<unsigned char, unsigned short,
  108. unsigned int, unsigned long, boost::ulong_long_type> unsigned_types;
  109. typedef mpl::list<float, double, long double> float_types;
  110. typedef int exponent_type;
  111. private:
  112. float128_type m_value;
  113. public:
  114. BOOST_CONSTEXPR float128_backend() BOOST_NOEXCEPT : m_value(0) {}
  115. BOOST_CONSTEXPR float128_backend(const float128_backend& o) BOOST_NOEXCEPT : m_value(o.m_value) {}
  116. float128_backend& operator = (const float128_backend& o) BOOST_NOEXCEPT
  117. {
  118. m_value = o.m_value;
  119. return *this;
  120. }
  121. template <class T>
  122. BOOST_CONSTEXPR float128_backend(const T& i, const typename enable_if_c<is_convertible<T, float128_type>::value>::type* = 0) BOOST_NOEXCEPT_IF(noexcept(std::declval<float128_type&>() = std::declval<const T&>()))
  123. : m_value(i) {}
  124. template <class T>
  125. typename enable_if_c<is_arithmetic<T>::value || is_convertible<T, float128_type>::value, float128_backend&>::type operator = (const T& i) BOOST_NOEXCEPT_IF(noexcept(std::declval<float128_type&>() = std::declval<const T&>()))
  126. {
  127. m_value = i;
  128. return *this;
  129. }
  130. float128_backend(long double const& f)
  131. {
  132. if(boost::math::isinf(f))
  133. m_value = (f < 0) ? -1.0Q / 0.0Q : 1.0Q / 0.0Q;
  134. else
  135. m_value = f;
  136. }
  137. float128_backend& operator=(long double const& f)
  138. {
  139. if(boost::math::isinf(f))
  140. m_value = (f < 0) ? -1.0Q / 0.0Q : 1.0Q / 0.0Q;
  141. else
  142. m_value = f;
  143. return *this;
  144. }
  145. float128_backend& operator = (const char* s)
  146. {
  147. #ifndef BOOST_MP_USE_QUAD
  148. char* p_end;
  149. m_value = strtoflt128(s, &p_end);
  150. if(p_end - s != (std::ptrdiff_t)std::strlen(s))
  151. {
  152. BOOST_THROW_EXCEPTION(std::runtime_error("Unable to interpret input string as a floating point value"));
  153. }
  154. #else
  155. boost::multiprecision::detail::convert_from_string(*this, s);
  156. #endif
  157. return *this;
  158. }
  159. void swap(float128_backend& o) BOOST_NOEXCEPT
  160. {
  161. std::swap(m_value, o.value());
  162. }
  163. std::string str(std::streamsize digits, std::ios_base::fmtflags f)const
  164. {
  165. #ifndef BOOST_MP_USE_QUAD
  166. char buf[100];
  167. boost::scoped_array<char> buf2;
  168. std::string format = "%";
  169. if(f & std::ios_base::showpos)
  170. format += "+";
  171. if(f & std::ios_base::showpoint)
  172. format += "#";
  173. format += ".*";
  174. if(digits == 0)
  175. digits = 36;
  176. format += "Q";
  177. if(f & std::ios_base::scientific)
  178. format += "e";
  179. else if(f & std::ios_base::fixed)
  180. format += "f";
  181. else
  182. format += "g";
  183. int v = quadmath_snprintf (buf, 100, format.c_str(), digits, m_value);
  184. if((v < 0) || (v >= 99))
  185. {
  186. int v_max = v;
  187. buf2.reset(new char[v+3]);
  188. v = quadmath_snprintf (&buf2[0], v_max + 3, format.c_str(), digits, m_value);
  189. if(v >= v_max + 3)
  190. {
  191. BOOST_THROW_EXCEPTION(std::runtime_error("Formatting of float128_type failed."));
  192. }
  193. return &buf2[0];
  194. }
  195. return buf;
  196. #else
  197. return boost::multiprecision::detail::convert_to_string(*this, digits ? digits : 37, f);
  198. #endif
  199. }
  200. void negate() BOOST_NOEXCEPT
  201. {
  202. m_value = -m_value;
  203. }
  204. int compare(const float128_backend& o)const
  205. {
  206. return m_value == o.m_value ? 0 : m_value < o.m_value ? -1 : 1;
  207. }
  208. template <class T>
  209. int compare(const T& i)const
  210. {
  211. return m_value == i ? 0 : m_value < i ? -1 : 1;
  212. }
  213. float128_type& value()
  214. {
  215. return m_value;
  216. }
  217. const float128_type& value()const
  218. {
  219. return m_value;
  220. }
  221. };
  222. inline void eval_add(float128_backend& result, const float128_backend& a)
  223. {
  224. result.value() += a.value();
  225. }
  226. template <class A>
  227. inline void eval_add(float128_backend& result, const A& a)
  228. {
  229. result.value() += a;
  230. }
  231. inline void eval_subtract(float128_backend& result, const float128_backend& a)
  232. {
  233. result.value() -= a.value();
  234. }
  235. template <class A>
  236. inline void eval_subtract(float128_backend& result, const A& a)
  237. {
  238. result.value() -= a;
  239. }
  240. inline void eval_multiply(float128_backend& result, const float128_backend& a)
  241. {
  242. result.value() *= a.value();
  243. }
  244. template <class A>
  245. inline void eval_multiply(float128_backend& result, const A& a)
  246. {
  247. result.value() *= a;
  248. }
  249. inline void eval_divide(float128_backend& result, const float128_backend& a)
  250. {
  251. result.value() /= a.value();
  252. }
  253. template <class A>
  254. inline void eval_divide(float128_backend& result, const A& a)
  255. {
  256. result.value() /= a;
  257. }
  258. inline void eval_add(float128_backend& result, const float128_backend& a, const float128_backend& b)
  259. {
  260. result.value() = a.value() + b.value();
  261. }
  262. template <class A>
  263. inline void eval_add(float128_backend& result, const float128_backend& a, const A& b)
  264. {
  265. result.value() = a.value() + b;
  266. }
  267. inline void eval_subtract(float128_backend& result, const float128_backend& a, const float128_backend& b)
  268. {
  269. result.value() = a.value() - b.value();
  270. }
  271. template <class A>
  272. inline void eval_subtract(float128_backend& result, const float128_backend& a, const A& b)
  273. {
  274. result.value() = a.value() - b;
  275. }
  276. template <class A>
  277. inline void eval_subtract(float128_backend& result, const A& a, const float128_backend& b)
  278. {
  279. result.value() = a - b.value();
  280. }
  281. inline void eval_multiply(float128_backend& result, const float128_backend& a, const float128_backend& b)
  282. {
  283. result.value() = a.value() * b.value();
  284. }
  285. template <class A>
  286. inline void eval_multiply(float128_backend& result, const float128_backend& a, const A& b)
  287. {
  288. result.value() = a.value() * b;
  289. }
  290. inline void eval_divide(float128_backend& result, const float128_backend& a, const float128_backend& b)
  291. {
  292. result.value() = a.value() / b.value();
  293. }
  294. template <class R>
  295. inline void eval_convert_to(R* result, const float128_backend& val)
  296. {
  297. *result = static_cast<R>(val.value());
  298. }
  299. inline void eval_frexp(float128_backend& result, const float128_backend& arg, int* exp)
  300. {
  301. result.value() = frexpq(arg.value(), exp);
  302. }
  303. inline void eval_ldexp(float128_backend& result, const float128_backend& arg, int exp)
  304. {
  305. result.value() = ldexpq(arg.value(), exp);
  306. }
  307. inline void eval_floor(float128_backend& result, const float128_backend& arg)
  308. {
  309. result.value() = floorq(arg.value());
  310. }
  311. inline void eval_ceil(float128_backend& result, const float128_backend& arg)
  312. {
  313. result.value() = ceilq(arg.value());
  314. }
  315. inline void eval_sqrt(float128_backend& result, const float128_backend& arg)
  316. {
  317. result.value() = sqrtq(arg.value());
  318. }
  319. inline int eval_fpclassify(const float128_backend& arg)
  320. {
  321. if(isnanq(arg.value()))
  322. return FP_NAN;
  323. else if(isinfq(arg.value()))
  324. return FP_INFINITE;
  325. else if(arg.value() == 0)
  326. return FP_ZERO;
  327. float128_backend t(arg);
  328. if(t.value() < 0)
  329. t.negate();
  330. if(t.value() < 3.36210314311209350626267781732175260e-4932Q)
  331. return FP_SUBNORMAL;
  332. return FP_NORMAL;
  333. }
  334. inline void eval_increment(float128_backend& arg)
  335. {
  336. ++arg.value();
  337. }
  338. inline void eval_decrement(float128_backend& arg)
  339. {
  340. --arg.value();
  341. }
  342. /*********************************************************************
  343. *
  344. * abs/fabs:
  345. *
  346. *********************************************************************/
  347. inline void eval_abs(float128_backend& result, const float128_backend& arg)
  348. {
  349. result.value() = fabsq(arg.value());
  350. }
  351. inline void eval_fabs(float128_backend& result, const float128_backend& arg)
  352. {
  353. result.value() = fabsq(arg.value());
  354. }
  355. /*********************************************************************
  356. *
  357. * Floating point functions:
  358. *
  359. *********************************************************************/
  360. inline void eval_trunc(float128_backend& result, const float128_backend& arg)
  361. {
  362. if(isnanq(arg.value()) || isinfq(arg.value()))
  363. {
  364. result = boost::math::policies::raise_rounding_error(
  365. "boost::multiprecision::trunc<%1%>(%1%)", 0,
  366. number<float128_backend, et_off>(arg),
  367. number<float128_backend, et_off>(arg),
  368. boost::math::policies::policy<>()).backend();
  369. return;
  370. }
  371. result.value() = truncq(arg.value());
  372. }
  373. /*
  374. //
  375. // This doesn't actually work... rely on our own default version instead.
  376. //
  377. inline void eval_round(float128_backend& result, const float128_backend& arg)
  378. {
  379. if(isnanq(arg.value()) || isinf(arg.value()))
  380. {
  381. result = boost::math::policies::raise_rounding_error(
  382. "boost::multiprecision::trunc<%1%>(%1%)", 0,
  383. number<float128_backend, et_off>(arg),
  384. number<float128_backend, et_off>(arg),
  385. boost::math::policies::policy<>()).backend();
  386. return;
  387. }
  388. result.value() = roundq(arg.value());
  389. }
  390. */
  391. inline void eval_exp(float128_backend& result, const float128_backend& arg)
  392. {
  393. result.value() = expq(arg.value());
  394. }
  395. inline void eval_log(float128_backend& result, const float128_backend& arg)
  396. {
  397. result.value() = logq(arg.value());
  398. }
  399. inline void eval_log10(float128_backend& result, const float128_backend& arg)
  400. {
  401. result.value() = log10q(arg.value());
  402. }
  403. inline void eval_sin(float128_backend& result, const float128_backend& arg)
  404. {
  405. result.value() = sinq(arg.value());
  406. }
  407. inline void eval_cos(float128_backend& result, const float128_backend& arg)
  408. {
  409. result.value() = cosq(arg.value());
  410. }
  411. inline void eval_tan(float128_backend& result, const float128_backend& arg)
  412. {
  413. result.value() = tanq(arg.value());
  414. }
  415. inline void eval_asin(float128_backend& result, const float128_backend& arg)
  416. {
  417. result.value() = asinq(arg.value());
  418. }
  419. inline void eval_acos(float128_backend& result, const float128_backend& arg)
  420. {
  421. result.value() = acosq(arg.value());
  422. }
  423. inline void eval_atan(float128_backend& result, const float128_backend& arg)
  424. {
  425. result.value() = atanq(arg.value());
  426. }
  427. inline void eval_sinh(float128_backend& result, const float128_backend& arg)
  428. {
  429. result.value() = sinhq(arg.value());
  430. }
  431. inline void eval_cosh(float128_backend& result, const float128_backend& arg)
  432. {
  433. result.value() = coshq(arg.value());
  434. }
  435. inline void eval_tanh(float128_backend& result, const float128_backend& arg)
  436. {
  437. result.value() = tanhq(arg.value());
  438. }
  439. inline void eval_fmod(float128_backend& result, const float128_backend& a, const float128_backend& b)
  440. {
  441. result.value() = fmodq(a.value(), b.value());
  442. }
  443. inline void eval_pow(float128_backend& result, const float128_backend& a, const float128_backend& b)
  444. {
  445. result.value() = powq(a.value(), b.value());
  446. }
  447. inline void eval_atan2(float128_backend& result, const float128_backend& a, const float128_backend& b)
  448. {
  449. result.value() = atan2q(a.value(), b.value());
  450. }
  451. } // namespace backends
  452. }} // namespaces
  453. namespace boost{
  454. namespace archive{
  455. class binary_oarchive;
  456. class binary_iarchive;
  457. }
  458. namespace serialization{ namespace float128_detail{
  459. template <class Archive>
  460. void do_serialize(Archive& ar, boost::multiprecision::backends::float128_backend& val, const mpl::false_&, const mpl::false_&)
  461. {
  462. // saving
  463. // non-binary
  464. std::string s(val.str(0, std::ios_base::scientific));
  465. ar & s;
  466. }
  467. template <class Archive>
  468. void do_serialize(Archive& ar, boost::multiprecision::backends::float128_backend& val, const mpl::true_&, const mpl::false_&)
  469. {
  470. // loading
  471. // non-binary
  472. std::string s;
  473. ar & s;
  474. val = s.c_str();
  475. }
  476. template <class Archive>
  477. void do_serialize(Archive& ar, boost::multiprecision::backends::float128_backend& val, const mpl::false_&, const mpl::true_&)
  478. {
  479. // saving
  480. // binary
  481. ar.save_binary(&val, sizeof(val));
  482. }
  483. template <class Archive>
  484. void do_serialize(Archive& ar, boost::multiprecision::backends::float128_backend& val, const mpl::true_&, const mpl::true_&)
  485. {
  486. // loading
  487. // binary
  488. ar.load_binary(&val, sizeof(val));
  489. }
  490. } // detail
  491. template <class Archive>
  492. void serialize(Archive& ar, boost::multiprecision::backends::float128_backend& val, unsigned int /*version*/)
  493. {
  494. typedef typename Archive::is_loading load_tag;
  495. typedef typename mpl::bool_<boost::is_same<Archive, boost::archive::binary_oarchive>::value || boost::is_same<Archive, boost::archive::binary_iarchive>::value> binary_tag;
  496. float128_detail::do_serialize(ar, val, load_tag(), binary_tag());
  497. }
  498. }}
  499. namespace std{
  500. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  501. class numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >
  502. {
  503. typedef boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> number_type;
  504. public:
  505. BOOST_STATIC_CONSTEXPR bool is_specialized = true;
  506. static number_type (min)() BOOST_NOEXCEPT { return 3.36210314311209350626267781732175260e-4932Q; }
  507. static number_type (max)() BOOST_NOEXCEPT { return 1.18973149535723176508575932662800702e4932Q; }
  508. static number_type lowest() BOOST_NOEXCEPT { return -(max)(); }
  509. BOOST_STATIC_CONSTEXPR int digits = 113;
  510. BOOST_STATIC_CONSTEXPR int digits10 = 33;
  511. BOOST_STATIC_CONSTEXPR int max_digits10 = 36;
  512. BOOST_STATIC_CONSTEXPR bool is_signed = true;
  513. BOOST_STATIC_CONSTEXPR bool is_integer = false;
  514. BOOST_STATIC_CONSTEXPR bool is_exact = false;
  515. BOOST_STATIC_CONSTEXPR int radix = 2;
  516. static number_type epsilon() { return 1.92592994438723585305597794258492732e-34Q; }
  517. static number_type round_error() { return 0.5; }
  518. BOOST_STATIC_CONSTEXPR int min_exponent = -16381;
  519. BOOST_STATIC_CONSTEXPR int min_exponent10 = min_exponent * 301L / 1000L;
  520. BOOST_STATIC_CONSTEXPR int max_exponent = 16384;
  521. BOOST_STATIC_CONSTEXPR int max_exponent10 = max_exponent * 301L / 1000L;
  522. BOOST_STATIC_CONSTEXPR bool has_infinity = true;
  523. BOOST_STATIC_CONSTEXPR bool has_quiet_NaN = true;
  524. BOOST_STATIC_CONSTEXPR bool has_signaling_NaN = false;
  525. BOOST_STATIC_CONSTEXPR float_denorm_style has_denorm = denorm_present;
  526. BOOST_STATIC_CONSTEXPR bool has_denorm_loss = true;
  527. static number_type infinity() { return 1.0q / 0.0q; }
  528. static number_type quiet_NaN() { return number_type("nan"); }
  529. static number_type signaling_NaN() { return 0; }
  530. static number_type denorm_min() { return 6.475175119438025110924438958227646552e-4966Q; }
  531. BOOST_STATIC_CONSTEXPR bool is_iec559 = true;
  532. BOOST_STATIC_CONSTEXPR bool is_bounded = false;
  533. BOOST_STATIC_CONSTEXPR bool is_modulo = false;
  534. BOOST_STATIC_CONSTEXPR bool traps = false;
  535. BOOST_STATIC_CONSTEXPR bool tinyness_before = false;
  536. BOOST_STATIC_CONSTEXPR float_round_style round_style = round_to_nearest;
  537. };
  538. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  539. BOOST_CONSTEXPR_OR_CONST bool numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::is_specialized;
  540. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  541. BOOST_CONSTEXPR_OR_CONST int numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::digits;
  542. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  543. BOOST_CONSTEXPR_OR_CONST int numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::digits10;
  544. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  545. BOOST_CONSTEXPR_OR_CONST int numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::max_digits10;
  546. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  547. BOOST_CONSTEXPR_OR_CONST bool numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::is_signed;
  548. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  549. BOOST_CONSTEXPR_OR_CONST bool numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::is_integer;
  550. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  551. BOOST_CONSTEXPR_OR_CONST bool numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::is_exact;
  552. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  553. BOOST_CONSTEXPR_OR_CONST int numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::radix;
  554. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  555. BOOST_CONSTEXPR_OR_CONST int numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::min_exponent;
  556. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  557. BOOST_CONSTEXPR_OR_CONST int numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::max_exponent;
  558. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  559. BOOST_CONSTEXPR_OR_CONST int numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::min_exponent10;
  560. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  561. BOOST_CONSTEXPR_OR_CONST int numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::max_exponent10;
  562. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  563. BOOST_CONSTEXPR_OR_CONST bool numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::has_infinity;
  564. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  565. BOOST_CONSTEXPR_OR_CONST bool numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::has_quiet_NaN;
  566. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  567. BOOST_CONSTEXPR_OR_CONST bool numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::has_signaling_NaN;
  568. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  569. BOOST_CONSTEXPR_OR_CONST bool numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::has_denorm_loss;
  570. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  571. BOOST_CONSTEXPR_OR_CONST bool numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::is_iec559;
  572. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  573. BOOST_CONSTEXPR_OR_CONST bool numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::is_bounded;
  574. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  575. BOOST_CONSTEXPR_OR_CONST bool numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::is_modulo;
  576. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  577. BOOST_CONSTEXPR_OR_CONST bool numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::traps;
  578. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  579. BOOST_CONSTEXPR_OR_CONST bool numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::tinyness_before;
  580. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  581. BOOST_CONSTEXPR_OR_CONST float_round_style numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::round_style;
  582. template <boost::multiprecision::expression_template_option ExpressionTemplates>
  583. BOOST_CONSTEXPR_OR_CONST float_denorm_style numeric_limits<boost::multiprecision::number<boost::multiprecision::backends::float128_backend, ExpressionTemplates> >::has_denorm;
  584. } // namespace std
  585. #endif