Auxiliary Arithmetic Algorithms
add.hpp
1 #pragma once
2 
3 #include <algorithm>
4 
5 #include "traits.hpp"
6 
7 namespace aaa {
8 
44 // iterators
46 
47 template<typename InputIterator1, typename InputIterator2, typename OutputIterator,
48  check_sum<value_type_i<InputIterator1>, value_type_i<InputIterator2>, value_type_i<OutputIterator>> = nullptr>
49  void add(InputIterator1 first_left, InputIterator1 last_left, InputIterator2 first_right, OutputIterator first_out)
50 {
51  auto f = [](const value_type_i<InputIterator1>& left, const value_type_i<InputIterator2>& right)
52  {
53  return left + right;
54  };
55  std::transform(first_left, last_left, first_right, first_out, f);
56 }
57 
58 template<typename Element, typename InputIterator, typename OutputIterator,
59  check_sum<Element, value_type_i<InputIterator>, value_type_i<OutputIterator>> = nullptr>
60  void add(const Element& left, InputIterator first_right, InputIterator last_right, OutputIterator first_out)
61 {
62  auto f = [&](const value_type_i<InputIterator>& right) { return left + right; };
63  std::transform(first_right, last_right, first_out, f);
64 }
65 
66 template<typename InputIterator, typename Element, typename OutputIterator,
67  check_sum<value_type_i<InputIterator>, Element, value_type_i<OutputIterator>> = nullptr>
68  void add(InputIterator first_left, InputIterator last_left, const Element& right, OutputIterator first_out)
69 {
70  auto f = [&](const value_type_i<InputIterator>& left) { return left + right; };
71  std::transform(first_left, last_left, first_out, f);
72 }
73 
74 
76 // containers
77 
78 template<typename Container1, typename Container2, typename Container3,
79  check_sum<value_type<Container1>, value_type<Container2>, value_type<Container3>> = nullptr>
80  void add(const Container1& left, const Container2& right, Container3& out)
81 {
82  assert(left.size() == out.size());
83  assert(right.size() == out.size());
84  using std::begin;
85  using std::end;
86  add(begin(left), end(left), begin(right), begin(out));
87 }
88 
89 template<typename Element, typename Container1, typename Container2,
90  check_sum<Element, value_type<Container1>, value_type<Container2>> = nullptr>
91  void add(const Element& left, const Container1& right, Container2& out)
92 {
93  assert(right.size() == out.size());
94  using std::begin;
95  using std::end;
96  add(left, begin(right), end(right), begin(out));
97 }
98 
99 template<typename Container1, typename Element, typename Container2,
100  check_sum<value_type<Container1>, Element, value_type<Container2>> = nullptr>
101  void add(const Container1& left, const Element& right, Container2& out)
102 {
103  assert(left.size() == out.size());
104  using std::begin;
105  using std::end;
106  add(begin(left), end(left), right, begin(out));
107 }
108 
110 // make container
111 
112 template<typename Container>
113 Container add(const Container& left, const Container& right)
114 {
115  auto out = left;
116  add(left, right, out);
117  return out;
118 }
119 
120 template<typename Container>
121 Container add(const Container& left, const value_type<Container>& right)
122 {
123  auto out = left;
124  add(left, right, out);
125  return out;
126 }
127 
128 template<typename Container>
129 Container add(const value_type<Container>& left, const Container& right)
130 {
131  auto out = right;
132  add(left, right, out);
133  return out;
134 }
135 
138 } // namespace aaa
Definition: add.hpp:7