explicit_conversion.hpp 2.4 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667
  1. ///////////////////////////////////////////////////////////////////////////////
  2. // Copyright Vicente J. Botet Escriba 2009-2011
  3. // Copyright 2012 John Maddock. Distributed under the Boost
  4. // Software License, Version 1.0. (See accompanying file
  5. // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  6. #ifndef BOOST_MP_EXPLICIT_CONVERSION_HPP
  7. #define BOOST_MP_EXPLICIT_CONVERSION_HPP
  8. #include <type_traits>
  9. #include <boost/multiprecision/detail/standalone_config.hpp>
  10. #include <boost/multiprecision/detail/number_base.hpp> // number_category
  11. namespace boost {
  12. namespace multiprecision {
  13. namespace detail {
  14. template <unsigned int N>
  15. struct dummy_size
  16. {};
  17. template <typename S, typename T>
  18. struct has_generic_interconversion
  19. {
  20. using type = typename std::conditional<
  21. is_number<S>::value && is_number<T>::value,
  22. typename std::conditional<
  23. number_category<S>::value == number_kind_integer,
  24. typename std::conditional<
  25. number_category<T>::value == number_kind_integer || number_category<T>::value == number_kind_floating_point || number_category<T>::value == number_kind_rational || number_category<T>::value == number_kind_fixed_point,
  26. std::true_type,
  27. std::false_type >::type,
  28. typename std::conditional<
  29. number_category<S>::value == number_kind_rational,
  30. typename std::conditional<
  31. number_category<T>::value == number_kind_rational || number_category<T>::value == number_kind_rational,
  32. std::true_type,
  33. std::false_type >::type,
  34. typename std::conditional<
  35. number_category<T>::value == number_kind_floating_point,
  36. std::true_type,
  37. std::false_type >::type>::type>::type,
  38. std::false_type >::type;
  39. };
  40. template <typename S, typename T>
  41. struct is_explicitly_convertible_imp
  42. {
  43. template <typename S1, typename T1>
  44. static int selector(dummy_size<static_cast<unsigned int>(sizeof(new T1(std::declval<S1>())))>*);
  45. template <typename S1, typename T1>
  46. static char selector(...);
  47. static constexpr bool value = sizeof(selector<S, T>(nullptr)) == sizeof(int);
  48. using type = std::integral_constant<bool, value>;
  49. };
  50. template <typename From, typename To>
  51. struct is_explicitly_convertible : public is_explicitly_convertible_imp<From, To>::type
  52. {
  53. };
  54. }}} // namespace boost::multiprecision::detail
  55. #endif