Toolbox snapshot
The Reactive C++ Toolbox
Loading...
Searching...
No Matches
IntTypes.hpp
Go to the documentation of this file.
1// The Reactive C++ Toolbox.
2// Copyright (C) 2013-2019 Swirly Cloud Limited
3// Copyright (C) 2022 Reactive Markets Limited
4//
5// Licensed under the Apache License, Version 2.0 (the "License");
6// you may not use this file except in compliance with the License.
7// You may obtain a copy of the License at
8//
9// http://www.apache.org/licenses/LICENSE-2.0
10//
11// Unless required by applicable law or agreed to in writing, software
12// distributed under the License is distributed on an "AS IS" BASIS,
13// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14// See the License for the specific language governing permissions and
15// limitations under the License.
16
17#ifndef TOOLBOX_UTIL_INTTYPES_HPP
18#define TOOLBOX_UTIL_INTTYPES_HPP
19
21
22#include <boost/functional/hash.hpp>
23
24namespace toolbox {
25inline namespace util {
26
27template <typename ValueT>
28struct IntPolicy {
30 static constexpr ValueT min() noexcept { return std::numeric_limits<ValueT>::min(); }
31 static constexpr ValueT max() noexcept { return std::numeric_limits<ValueT>::max(); }
32};
36
37template <typename PolicyT>
39 using ValueType = typename PolicyT::ValueType;
40
41 template <typename RhsT>
42 requires std::convertible_to<RhsT, ValueType>
43 constexpr explicit IntWrapper(RhsT rhs) noexcept
44 : value_{static_cast<ValueType>(rhs)}
45 {
46 }
47
48 constexpr IntWrapper() noexcept = default;
49 ~IntWrapper() = default;
50
51 // Copy.
52 constexpr IntWrapper(const IntWrapper&) noexcept = default;
53 constexpr IntWrapper& operator=(const IntWrapper&) noexcept = default;
54
55 // Move.
56 constexpr IntWrapper(IntWrapper&&) noexcept = default;
57 constexpr IntWrapper& operator=(IntWrapper&&) noexcept = default;
58
59 constexpr ValueType count() const noexcept { return value_; }
60
61 static constexpr IntWrapper min() noexcept { return PolicyT::min(); }
62 static constexpr IntWrapper max() noexcept { return PolicyT::max(); }
63 static constexpr IntWrapper zero() noexcept { return IntWrapper{0}; }
64
65 // Assignment.
66
68 constexpr IntWrapper& operator+=(IntWrapper rhs) noexcept
69 {
70 value_ += rhs.value_;
71 return *this;
72 }
73
75 constexpr IntWrapper& operator-=(IntWrapper rhs) noexcept
76 {
77 value_ -= rhs.value_;
78 return *this;
79 }
80
82 constexpr IntWrapper& operator*=(IntWrapper rhs) noexcept
83 {
84 value_ *= rhs.value_;
85 return *this;
86 }
87
89 constexpr IntWrapper& operator/=(IntWrapper rhs) noexcept
90 {
91 value_ /= rhs.value_;
92 return *this;
93 }
94
96 constexpr IntWrapper& operator%=(IntWrapper rhs) noexcept
97 {
98 value_ %= rhs.value_;
99 return *this;
100 }
101
103 constexpr IntWrapper& operator&=(IntWrapper rhs) noexcept
104 {
105 value_ &= rhs.value_;
106 return *this;
107 }
108
110 constexpr IntWrapper& operator|=(IntWrapper rhs) noexcept
111 {
112 value_ |= rhs.value_;
113 return *this;
114 }
115
117 constexpr IntWrapper& operator^=(IntWrapper rhs) noexcept
118 {
119 value_ ^= rhs.value_;
120 return *this;
121 }
122
124 constexpr IntWrapper& operator<<=(IntWrapper rhs) noexcept
125 {
126 value_ <<= rhs.value_;
127 return *this;
128 }
129
131 constexpr IntWrapper& operator>>=(IntWrapper rhs) noexcept
132 {
133 value_ >>= rhs.value_;
134 return *this;
135 }
136
137 // Increment/Decrement.
138
140 constexpr IntWrapper& operator++() noexcept
141 {
142 ++value_;
143 return *this;
144 }
145
147 constexpr IntWrapper& operator--() noexcept
148 {
149 --value_;
150 return *this;
151 }
152
154 constexpr IntWrapper operator++(int) noexcept { return IntWrapper{value_++}; }
155
157 constexpr IntWrapper operator--(int) noexcept { return IntWrapper{value_--}; }
158
159 // Arithmetic.
160
162 constexpr IntWrapper operator+() const noexcept { return IntWrapper{+value_}; }
163
165 constexpr IntWrapper operator-() const noexcept { return IntWrapper{-value_}; }
166
168 friend constexpr IntWrapper operator+(IntWrapper lhs, IntWrapper rhs) noexcept
169 {
170 return IntWrapper{lhs.value_ + rhs.value_};
171 }
172
174 friend constexpr IntWrapper operator-(IntWrapper lhs, IntWrapper rhs) noexcept
175 {
176 return IntWrapper{lhs.value_ - rhs.value_};
177 }
178
180 friend constexpr IntWrapper operator*(IntWrapper lhs, IntWrapper rhs) noexcept
181 {
182 return IntWrapper{lhs.value_ * rhs.value_};
183 }
184
186 friend constexpr IntWrapper operator/(IntWrapper lhs, IntWrapper rhs) noexcept
187 {
188 return IntWrapper{lhs.value_ / rhs.value_};
189 }
190
192 friend constexpr IntWrapper operator%(IntWrapper lhs, IntWrapper rhs) noexcept
193 {
194 return IntWrapper{lhs.value_ % rhs.value_};
195 }
196
197 // Bitwise.
198
200 constexpr IntWrapper operator~() const noexcept { return IntWrapper{~value_}; }
201
203 friend constexpr IntWrapper operator&(IntWrapper lhs, IntWrapper rhs) noexcept
204 {
205 return IntWrapper{lhs.value_ & rhs.value_};
206 }
207
209 friend constexpr IntWrapper operator|(IntWrapper lhs, IntWrapper rhs) noexcept
210 {
211 return IntWrapper{lhs.value_ | rhs.value_};
212 }
213
215 friend constexpr IntWrapper operator^(IntWrapper lhs, IntWrapper rhs) noexcept
216 {
217 return IntWrapper{lhs.value_ ^ rhs.value_};
218 }
219
221 friend constexpr IntWrapper operator<<(IntWrapper lhs, IntWrapper rhs) noexcept
222 {
223 return IntWrapper{lhs.value_ << rhs.value_};
224 }
225
227 friend constexpr IntWrapper operator>>(IntWrapper lhs, IntWrapper rhs) noexcept
228 {
229 return IntWrapper{lhs.value_ >> rhs.value_};
230 }
231
232 // Comparison.
233 friend constexpr auto operator<=>(const IntWrapper&, const IntWrapper&) noexcept = default;
234 friend constexpr bool operator==(const IntWrapper&, const IntWrapper&) noexcept = default;
235
236 // Stream.
237
239 friend constexpr std::ostream& operator<<(std::ostream& os, IntWrapper rhs)
240 {
241 return os << rhs.value_;
242 }
243
244 private:
245 ValueType value_;
246};
247
250static_assert(std::is_standard_layout_v<IntWrapper<Int32Policy>>
251 && std::is_trivial_v<IntWrapper<Int32Policy>>);
252static_assert(sizeof(IntWrapper<Int16Policy>) == 2, "must be specific size");
253static_assert(sizeof(IntWrapper<Int32Policy>) == 4, "must be specific size");
254static_assert(sizeof(IntWrapper<Int64Policy>) == 8, "must be specific size");
255
256template <typename ValueT>
257concept IsIntWrapper = is_instantiation_of<ValueT, IntWrapper>::value;
258
259template <typename PolicyT>
261{
262 boost::hash<typename PolicyT::ValueType> hasher;
263 return hasher(wrapper.count());
264}
265
266template <typename ValueT>
267 requires IsIntWrapper<ValueT>
269 static constexpr auto from_string(std::string_view sv) noexcept
270 {
272 return ValueT{UnderlyingTraits::from_string(sv)};
273 }
274};
275
279
282
283constexpr Id16 operator""_id16(unsigned long long val) noexcept
284{
285 return Id16{val};
286}
287
290
291constexpr Id32 operator""_id32(unsigned long long val) noexcept
292{
293 return Id32{val};
294}
295
298
299constexpr Id64 operator""_id64(unsigned long long val) noexcept
300{
301 return Id64{val};
302}
303
304} // namespace util
305} // namespace toolbox
306
307namespace std {
308template <typename PolicyT>
309struct hash<toolbox::IntWrapper<PolicyT>> {
310 inline std::size_t operator()(toolbox::IntWrapper<PolicyT> wrapper) const
311 {
312 return wrapper.count();
313 }
314};
315} // namespace std
316
317#endif // TOOLBOX_UTIL_INTTYPES_HPP
#define TOOLBOX_PACKED
Definition Config.h:29
STL namespace.
std::size_t hash_value(IntWrapper< PolicyT > wrapper)
Definition IntTypes.hpp:260
std::string_view sv
Definition Tokeniser.hpp:26
constexpr auto bind() noexcept
Definition Slot.hpp:92
std::size_t operator()(toolbox::IntWrapper< PolicyT > wrapper) const
Definition IntTypes.hpp:310
static constexpr ValueT max() noexcept
Definition IntTypes.hpp:31
static constexpr ValueT min() noexcept
Definition IntTypes.hpp:30
friend constexpr std::ostream & operator<<(std::ostream &os, IntWrapper rhs)
Insertion.
Definition IntTypes.hpp:239
friend constexpr bool operator==(const IntWrapper &, const IntWrapper &) noexcept=default
friend constexpr IntWrapper operator-(IntWrapper lhs, IntWrapper rhs) noexcept
Subtraction.
Definition IntTypes.hpp:174
friend constexpr IntWrapper operator+(IntWrapper lhs, IntWrapper rhs) noexcept
Addition.
Definition IntTypes.hpp:168
constexpr IntWrapper() noexcept=default
constexpr IntWrapper & operator|=(IntWrapper rhs) noexcept
Bitwise OR assignment.
Definition IntTypes.hpp:110
friend constexpr IntWrapper operator^(IntWrapper lhs, IntWrapper rhs) noexcept
Bitwise XOR.
Definition IntTypes.hpp:215
constexpr IntWrapper & operator-=(IntWrapper rhs) noexcept
Subtraction assignment.
Definition IntTypes.hpp:75
constexpr IntWrapper & operator>>=(IntWrapper rhs) noexcept
Bitwise right shift assignment.
Definition IntTypes.hpp:131
constexpr IntWrapper & operator^=(IntWrapper rhs) noexcept
Bitwise XOR assignment.
Definition IntTypes.hpp:117
typename PolicyT::ValueType ValueType
Definition IntTypes.hpp:39
friend constexpr IntWrapper operator*(IntWrapper lhs, IntWrapper rhs) noexcept
Multiplication.
Definition IntTypes.hpp:180
friend constexpr IntWrapper operator|(IntWrapper lhs, IntWrapper rhs) noexcept
Bitwise OR.
Definition IntTypes.hpp:209
constexpr IntWrapper operator-() const noexcept
Unary minus.
Definition IntTypes.hpp:165
friend constexpr IntWrapper operator&(IntWrapper lhs, IntWrapper rhs) noexcept
Bitwise AND.
Definition IntTypes.hpp:203
constexpr IntWrapper & operator*=(IntWrapper rhs) noexcept
Multiplication assignment.
Definition IntTypes.hpp:82
constexpr IntWrapper operator~() const noexcept
Bitwise NOT.
Definition IntTypes.hpp:200
friend constexpr IntWrapper operator<<(IntWrapper lhs, IntWrapper rhs) noexcept
Bitwise left shift.
Definition IntTypes.hpp:221
constexpr IntWrapper operator+() const noexcept
Unary plus.
Definition IntTypes.hpp:162
static constexpr IntWrapper min() noexcept
Definition IntTypes.hpp:61
constexpr IntWrapper operator--(int) noexcept
Post-decrement.
Definition IntTypes.hpp:157
constexpr IntWrapper & operator++() noexcept
Pre-increment.
Definition IntTypes.hpp:140
friend constexpr IntWrapper operator>>(IntWrapper lhs, IntWrapper rhs) noexcept
Bitwise right shift.
Definition IntTypes.hpp:227
constexpr IntWrapper & operator--() noexcept
Pre-decrement.
Definition IntTypes.hpp:147
friend constexpr IntWrapper operator%(IntWrapper lhs, IntWrapper rhs) noexcept
Modulo.
Definition IntTypes.hpp:192
constexpr IntWrapper & operator<<=(IntWrapper rhs) noexcept
Bitwise left shift assignment.
Definition IntTypes.hpp:124
constexpr IntWrapper operator++(int) noexcept
Post-increment.
Definition IntTypes.hpp:154
constexpr IntWrapper & operator%=(IntWrapper rhs) noexcept
Modulo assignment.
Definition IntTypes.hpp:96
constexpr ValueType count() const noexcept
Definition IntTypes.hpp:59
static constexpr IntWrapper zero() noexcept
Definition IntTypes.hpp:63
friend constexpr IntWrapper operator/(IntWrapper lhs, IntWrapper rhs) noexcept
Division.
Definition IntTypes.hpp:186
friend constexpr auto operator<=>(const IntWrapper &, const IntWrapper &) noexcept=default
static constexpr IntWrapper max() noexcept
Definition IntTypes.hpp:62
constexpr IntWrapper & operator+=(IntWrapper rhs) noexcept
Addition assignment.
Definition IntTypes.hpp:68
constexpr IntWrapper & operator&=(IntWrapper rhs) noexcept
Bitwise AND assignment.
Definition IntTypes.hpp:103
constexpr IntWrapper(RhsT rhs) noexcept
Definition IntTypes.hpp:43
constexpr IntWrapper & operator/=(IntWrapper rhs) noexcept
Division assignment.
Definition IntTypes.hpp:89
static constexpr auto from_string(std::string_view sv) noexcept
Definition IntTypes.hpp:269