cnumeric.hpp 1.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566
  1. // Copyright Louis Dionne 2013-2017
  2. // Distributed under the Boost Software License, Version 1.0.
  3. // (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt)
  4. #ifndef TEST_SUPPORT_CNUMERIC_HPP
  5. #define TEST_SUPPORT_CNUMERIC_HPP
  6. #include <boost/hana/concept/integral_constant.hpp>
  7. #include <boost/hana/core/when.hpp>
  8. #include <boost/hana/fwd/core/to.hpp>
  9. #include <boost/hana/fwd/equal.hpp>
  10. #include <boost/hana/fwd/less.hpp>
  11. template <typename T>
  12. struct CNumeric { using value_type = T; };
  13. template <typename T, T v>
  14. struct cnumeric_t {
  15. static constexpr T value = v;
  16. using hana_tag = CNumeric<T>;
  17. constexpr operator T() const { return value; }
  18. };
  19. template <typename T, T v>
  20. constexpr cnumeric_t<T, v> cnumeric{};
  21. template <typename T, T v>
  22. constexpr cnumeric_t<T, v> make_cnumeric() { return {}; }
  23. namespace boost { namespace hana {
  24. // Constant and IntegralConstant
  25. template <typename T>
  26. struct IntegralConstant<CNumeric<T>> {
  27. static constexpr bool value = true;
  28. };
  29. template <typename T, typename C>
  30. struct to_impl<CNumeric<T>, C, when<
  31. hana::IntegralConstant<C>::value
  32. >>
  33. : embedding<is_embedded<typename C::value_type, T>::value>
  34. {
  35. template <typename N>
  36. static constexpr auto apply(N const&)
  37. { return cnumeric<T, N::value>; }
  38. };
  39. // Comparable
  40. template <typename T, typename U>
  41. struct equal_impl<CNumeric<T>, CNumeric<U>> {
  42. template <typename X, typename Y>
  43. static constexpr auto apply(X const&, Y const&)
  44. { return cnumeric<bool, X::value == Y::value>; }
  45. };
  46. // Orderable
  47. template <typename T, typename U>
  48. struct less_impl<CNumeric<T>, CNumeric<U>> {
  49. template <typename X, typename Y>
  50. static constexpr auto apply(X const&, Y const&)
  51. { return cnumeric<bool, (X::value < Y::value)>; }
  52. };
  53. }} // end namespace boost::hana
  54. #endif // !TEST_SUPPORT_CNUMERIC_HPP