CNL  2.0.2 (development)
Compositional Numeric Library
overloads.h
1 
2 // Copyright John McFarlane 2019.
3 // Distributed under the Boost Software License, Version 1.0.
4 // (See accompanying file ../LICENSE_1_0.txt or copy at
5 // http://www.boost.org/LICENSE_1_0.txt)
6 
7 #if !defined(CNL_IMPL_TAG_TAG_OVERLOADS_H)
8 #define CNL_IMPL_TAG_TAG_OVERLOADS_H
9 
10 #include "../num_traits/set_width.h"
11 #include "../num_traits/width.h"
12 #include "../numbers/set_signedness.h"
13 #include "../numbers/signedness.h"
14 #include "definition.h"
15 
16 #include <algorithm>
17 
19 namespace cnl {
20  namespace _impl {
21  template<
22  binary_arithmetic_op Operator, int LhsDigits, typename LhsNarrowest, int RhsDigits,
23  typename RhsNarrowest>
24  struct wide_tag_overload_params {
25  static constexpr bool is_signed{
26  numbers::signedness_v<LhsNarrowest> | numbers::signedness_v<RhsNarrowest>};
27  static constexpr int digits{std::max(LhsDigits, RhsDigits)};
28 
29  using narrowest = _impl::set_width_t<
30  numbers::set_signedness_t<
31  _impl::op_result<Operator, LhsNarrowest, RhsNarrowest>, is_signed>,
32  std::max(
33  _impl::width<LhsNarrowest>, _impl::width<RhsNarrowest>)>;
34 
35  using type = cnl::wide_tag<digits, narrowest>;
36  };
37  }
38 
39  template<int LhsDigits, typename LhsNarrowest, int RhsDigits, typename RhsNarrowest>
40  [[nodiscard]] constexpr auto operator+(
41  cnl::wide_tag<LhsDigits, LhsNarrowest>, cnl::wide_tag<RhsDigits, RhsNarrowest>) ->
42  typename _impl::wide_tag_overload_params<
43  _impl::add_op, LhsDigits, LhsNarrowest, RhsDigits, RhsNarrowest>::type
44  {
45  return typename _impl::wide_tag_overload_params<
46  _impl::add_op, LhsDigits, LhsNarrowest, RhsDigits, RhsNarrowest>::type{};
47  }
48 
49  template<int LhsDigits, typename LhsNarrowest, int RhsDigits, typename RhsNarrowest>
50  [[nodiscard]] constexpr auto operator-(
51  cnl::wide_tag<LhsDigits, LhsNarrowest>, cnl::wide_tag<RhsDigits, RhsNarrowest>) ->
52  typename _impl::wide_tag_overload_params<
53  _impl::subtract_op, LhsDigits, LhsNarrowest, RhsDigits, RhsNarrowest>::type
54  {
55  return typename _impl::wide_tag_overload_params<
56  _impl::subtract_op, LhsDigits, LhsNarrowest, RhsDigits, RhsNarrowest>::type{};
57  }
58 
59  template<int LhsDigits, typename LhsNarrowest, int RhsDigits, typename RhsNarrowest>
60  [[nodiscard]] constexpr auto operator*(
61  cnl::wide_tag<LhsDigits, LhsNarrowest>, cnl::wide_tag<RhsDigits, RhsNarrowest>) ->
62  typename _impl::wide_tag_overload_params<
63  _impl::multiply_op, LhsDigits, LhsNarrowest, RhsDigits, RhsNarrowest>::type
64  {
65  return typename _impl::wide_tag_overload_params<
66  _impl::multiply_op, LhsDigits, LhsNarrowest, RhsDigits, RhsNarrowest>::type{};
67  }
68 
69  template<int LhsDigits, typename LhsNarrowest, int RhsDigits, typename RhsNarrowest>
70  [[nodiscard]] constexpr auto operator/(
71  cnl::wide_tag<LhsDigits, LhsNarrowest>, cnl::wide_tag<RhsDigits, RhsNarrowest>) ->
72  typename _impl::wide_tag_overload_params<
73  _impl::divide_op, LhsDigits, LhsNarrowest, RhsDigits, RhsNarrowest>::type
74  {
75  return typename _impl::wide_tag_overload_params<
76  _impl::divide_op, LhsDigits, LhsNarrowest, RhsDigits, RhsNarrowest>::type{};
77  }
78 
79  template<int LhsDigits, typename LhsNarrowest, int RhsDigits, typename RhsNarrowest>
80  [[nodiscard]] constexpr auto operator%(
81  cnl::wide_tag<LhsDigits, LhsNarrowest>, cnl::wide_tag<RhsDigits, RhsNarrowest>) ->
82  typename _impl::wide_tag_overload_params<
83  _impl::modulo_op, LhsDigits, LhsNarrowest, RhsDigits, RhsNarrowest>::type
84  {
85  return typename _impl::wide_tag_overload_params<
86  _impl::modulo_op, LhsDigits, LhsNarrowest, RhsDigits, RhsNarrowest>::type{};
87  }
88 
89  template<int LhsDigits, typename LhsNarrowest, int RhsDigits, typename RhsNarrowest>
90  [[nodiscard]] constexpr auto operator&(
91  cnl::wide_tag<LhsDigits, LhsNarrowest>, cnl::wide_tag<RhsDigits, RhsNarrowest>) ->
92  typename _impl::wide_tag_overload_params<
93  _impl::bitwise_and_op, LhsDigits, LhsNarrowest, RhsDigits, RhsNarrowest>::type
94  {
95  return typename _impl::wide_tag_overload_params<
96  _impl::bitwise_and_op, LhsDigits, LhsNarrowest, RhsDigits, RhsNarrowest>::type{};
97  }
98 }
99 
100 #endif // CNL_IMPL_TAG_TAG_OVERLOADS_H
cnl
compositional numeric library
Definition: abort.h:15
std::max
T max(T... args)