Arene Base
Fundamental Utilities For Safety Critical C++
Loading...
Searching...
No Matches
array.hpp
Go to the documentation of this file.
1// Copyright 2024, Toyota Motor Corporation
2//
3// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
4
5#ifndef INCLUDE_GUARD_ARENE_BASE_ARENE_BASE_ARRAY_ARRAY_HPP_
6#define INCLUDE_GUARD_ARENE_BASE_ARENE_BASE_ARRAY_ARRAY_HPP_
7
8// IWYU pragma: private, include "arene/base/array.hpp"
9// IWYU pragma: friend "(arene/base(?!/tests)|stdlib/include/stdlib_detail)/.*"
10
11// parasoft-begin-suppress AUTOSAR-A16_2_2-a-2 "Arene Base aggregate headers permitted by A16-2-2 Permit #1"
12#include "arene/base/algorithm/equal.hpp"
13#include "arene/base/algorithm/lexicographical_compare.hpp"
14#include "arene/base/compare/compare_three_way.hpp"
15#include "arene/base/compare/operators.hpp"
16#include "arene/base/compare/strong_ordering.hpp"
17#include "arene/base/compiler_support/attributes.hpp"
18#include "arene/base/constraints/constraints.hpp"
19#include "arene/base/contracts/contract.hpp"
20#include "arene/base/detail/exceptions.hpp"
21#include "arene/base/span/span.hpp"
22#include "arene/base/stdlib_choice/cstddef.hpp"
23#include "arene/base/stdlib_choice/enable_if.hpp"
24#include "arene/base/stdlib_choice/integer_sequence.hpp"
25#include "arene/base/stdlib_choice/integral_constant.hpp"
26#include "arene/base/stdlib_choice/is_array.hpp"
27#include "arene/base/stdlib_choice/is_constructible.hpp"
28#include "arene/base/stdlib_choice/is_copy_assignable.hpp"
29#include "arene/base/stdlib_choice/is_move_constructible.hpp"
30#include "arene/base/stdlib_choice/is_same.hpp"
31#include "arene/base/stdlib_choice/move.hpp"
32#include "arene/base/stdlib_choice/remove_cv.hpp"
33#include "arene/base/stdlib_choice/remove_reference.hpp"
34#include "arene/base/stdlib_choice/tuple_element.hpp"
35#include "arene/base/stdlib_choice/tuple_size.hpp"
36#include "arene/base/type_traits/comparison_traits.hpp"
37#include "arene/base/type_traits/is_swappable.hpp"
38#include "arene/base/type_traits/remove_cvref.hpp"
39#include "arene/base/utility/swap.hpp"
40// parasoft-end-suppress AUTOSAR-A16_2_2-a-2
41
42// parasoft-begin-suppress AUTOSAR-A13_5_5-b-2 "Mixed comparisons permitted by A13-5-5 Permit #1"
43
44namespace arene {
45namespace base {
46
47namespace array_detail {
48/// @brief If exceptions are enabled, throws out of range. Otherwise, is an invariant violation as it should not be
49/// called.
50/// @note We have to use this method rather than the mixin because array must be an aggregate type, and in C++14 that
51/// means no base classes.
52/// @throws std::out_of_range if exceptions are enabled.
53ARENE_NORETURN void throw_out_of_range();
54} // namespace array_detail
55
56// parasoft-begin-suppress AUTOSAR-A2_10_1-e "False positive: arene::base::array members cannot hide extents members"
57// parasoft-begin-suppress AUTOSAR-A12_1_1-b-2 "False positive: arene::base::array models std::array, which is an
58// Aggregate, and has no constructors"
59/// @brief A fixed-size array of T objects.
60///
61/// This is a backport of the @c constexpr @c std::array from C++17.
62/// @tparam T The type of the element held by the array
63/// @tparam N The number of elements in the array
64template <typename T, std::size_t N>
65class array {
66 public:
67 // parasoft-begin-suppress AUTOSAR-A2_10_1-e "False positive: Identifiers do not hide content in unrelated class span"
68 /// @brief The type of each array element
69 using value_type = T;
70 /// @brief The type of a pointer to an array element
71 using pointer = T*;
72 /// @brief The type of a pointer to a const array element
73 using const_pointer = T const*;
74 /// @brief The type of a reference to an array element
75 using reference = T&;
76 /// @brief The type of a reference to a const array element
77 using const_reference = T const&;
78 /// @brief The type returned by @c size()
79 using size_type = std::size_t;
80 /// @brief The type for the distance between two iterators
81 using difference_type = std::ptrdiff_t;
82
83 /// @brief An iterator for the array
84 using iterator = typename span<T, N>::iterator;
85 /// @brief An iterator for the array that treats the elements as @c const
86 using const_iterator = typename span<T const, N>::iterator;
87
88 /// @brief An iterator for iteration through the array in reverse order.
89 using reverse_iterator = typename span<T, N>::reverse_iterator;
90 /// @brief An iterator for iteration through the array in reverse order that treats the elements as @c const.
91 using const_reverse_iterator = typename span<T, N>::const_reverse_iterator;
92
93 // parasoft-begin-suppress AUTOSAR-M11_0_1-a-2 "False positive: this is not 'member data', it is a public property,
94 // exposed as part of the API"
95 /// @brief The number of elements in the array, which is always @c N
96 /// @return The size of the array, N
97 static constexpr std::integral_constant<std::size_t, N> size{};
98 // parasoft-end-suppress AUTOSAR-M11_0_1-a-2
99
100 // parasoft-end-suppress AUTOSAR-A2_10_1-e "False positive: Identifiers do not hide content in unrelated class span"
101
102 // parasoft-begin-suppress AUTOSAR-A2_10_1-e "False positive: 'max_size' does not hide anything"
103 // parasoft-begin-suppress AUTOSAR-M11_0_1-a-2 "False positive: this is not 'member data', it is a public property,
104 // exposed as part of the API"
105 /// @brief The maximum number of elements in the array, which is always @c N
106 /// @return The size of the array, N
107 static constexpr std::integral_constant<std::size_t, N> max_size{};
108 // parasoft-end-suppress AUTOSAR-M11_0_1-a-2
109 // parasoft-end-suppress AUTOSAR-A2_10_1-e
110
111 // parasoft-begin-suppress AUTOSAR-A2_10_1-e "False positive: 'empty' does not hide anything"
112 // parasoft-begin-suppress AUTOSAR-M11_0_1-a-2 "False positive: this is not 'member data', it is a public property,
113 // exposed as part of the API"
114 /// @brief Check if the array is empty, always @c false
115 /// @return false
116 static constexpr std::integral_constant<bool, false> empty{};
117 // parasoft-end-suppress AUTOSAR-M11_0_1-a-2
118 // parasoft-end-suppress AUTOSAR-A2_10_1-e
119
120 /// @brief Obtain a pointer to the first element of the array.
121 /// @return a pointer to the first element of the array.
122 constexpr auto data() noexcept -> T* { return values_; }
123
124 /// @brief Obtain a pointer to the first element of the array.
125 /// @return a pointer to the first element of the array, const-qualified.
126 constexpr auto data() const noexcept -> T const* { return values_; }
127
128 /// @brief Obtain an iterator to the first element of the array.
129 /// @return an @c iterator that references the first element of the array.
130 constexpr auto begin() noexcept -> iterator { return span<T, N>{values_}.begin(); }
131
132 /// @brief Obtain an iterator to the one-passed-the-end of the array.
133 /// @return an @c iterator that references one-past the last element of the array.
134 constexpr auto end() noexcept -> iterator { return span<T, N>{values_}.end(); }
135
136 /// @brief Obtain an iterator to the first element of the array.
137 /// @return a @c const_iterator that references the first element of the array.
138 constexpr auto begin() const noexcept -> const_iterator { return span<T const, N>{values_}.begin(); }
139
140 /// @brief Obtain an iterator to the one-passed-the-end of the array.
141 /// @return a @c const_iterator that references one past the last element of the array.
142 constexpr auto end() const noexcept -> const_iterator { return span<T const, N>{values_}.end(); }
143
144 /// @brief Obtain a reverse_iterator to the last element of the array.
145 /// @return a @c reverse_iterator that references the last element of the array.
146 constexpr auto rbegin() noexcept -> reverse_iterator { return span<T, N>{values_}.rbegin(); }
147
148 /// @brief Obtain a @c reverse_iterator that references one-before the first element of the array.
149 /// @return a @c reverse_iterator that references one-before the first element of the array.
150 constexpr auto rend() noexcept -> reverse_iterator { return span<T, N>{values_}.rend(); }
151
152 /// @brief Obtain a reverse_iterator to the last element of the array.
153 /// @return a @c const_reverse_iterator that references the last element of the array.
154 constexpr auto rbegin() const noexcept -> const_reverse_iterator { return span<T const, N>{values_}.rbegin(); }
155
156 /// @brief Obtai a @c const_reverse_iterator that references one before the first element of the array.
157 /// @return a @c const_reverse_iterator that references one before the first element of the array.
158 constexpr auto rend() const noexcept -> const_reverse_iterator { return span<T const, N>{values_}.rend(); }
159
160 /// @brief Obtain a @c const_iterator that references the first element of the array.
161 /// @return a @c const_iterator that references the first element of the array.
162 constexpr auto cbegin() const noexcept -> const_iterator { return span<T const, N>{values_}.begin(); }
163
164 /// @brief Obtain a @c const_iterator that references one past the last element of the array.
165 /// @return a @c const_iterator that references one past the last element of the array.
166 constexpr auto cend() const noexcept -> const_iterator { return span<T const, N>{values_}.end(); }
167
168 /// @brief Obtain a @c const_reverse_iterator that references the last element of the array.
169 /// @return a @c const_reverse_iterator that references the last element of the array.
170 constexpr auto crbegin() const noexcept -> const_reverse_iterator { return span<T const, N>{values_}.rbegin(); }
171
172 /// @brief Obtain a @c const_reverse_iterator that references one before the first element of the array.
173 /// @return a @c const_reverse_iterator that references one before the first element of the array.
174 constexpr auto crend() const noexcept -> const_reverse_iterator { return span<T const, N>{values_}.rend(); }
175
176 /// @brief Get a reference to the n'th element of the array.
177 ///
178 /// @param index The index of the element to access.
179 /// @pre @c index Must be less than @c N or else @c ARENE_PRECONDITION violation.
180 /// @return A reference to that element
181 constexpr auto operator[](std::size_t index) noexcept -> T& {
182 ARENE_PRECONDITION(index < size());
183 return values_[index];
184 }
185 /// @brief Get a reference to the n'th element of the array.
186 ///
187 /// @param index The index of the element to access.
188 /// @pre @c index Must be less than @c N or else @c ARENE_PRECONDITION violation.
189 /// @return A reference to that element
190 constexpr auto operator[](std::size_t index) const noexcept -> T const& {
191 ARENE_PRECONDITION(index < size());
192 return values_[index];
193 }
194
195 /// @brief Get a reference to the n'th element of the array, or throw.
196 ///
197 /// @tparam AreExceptionsEnabled SFINAE flag to disable this method if exceptions are not enabled. Should not be
198 /// specified by the user.
199 /// @param index The index of the element to access.
200 /// @return A reference to that element
201 /// @throws std::out_of_range If index is not less than @c N
202 template <
203 bool AreExceptionsEnabled = detail::are_exceptions_enabled::value,
204 constraints<std::enable_if_t<AreExceptionsEnabled>> = nullptr>
205 constexpr auto at(std::size_t index) -> T& {
206 if (index >= size()) {
207 array_detail::throw_out_of_range();
208 }
209 return values_[index];
210 }
211 /// @brief Get a reference to the n'th element of the array, or throw.
212 ///
213 /// @tparam AreExceptionsEnabled Defaulted SFINAE flag to disable this method if exceptions are not enabled; should
214 /// not be specified by user.
215 /// @param index The index of the element to access.
216 /// @return A reference to that element
217 /// @throws std::out_of_range If index is not less than @c N
218 template <
219 bool AreExceptionsEnabled = detail::are_exceptions_enabled::value,
220 constraints<std::enable_if_t<AreExceptionsEnabled>> = nullptr>
221 constexpr auto at(std::size_t index) const -> T const& {
222 if (index >= size()) {
223 array_detail::throw_out_of_range();
224 }
225 return values_[index];
226 }
227
228 /// @brief Get a reference to the first element of the array.
229 ///
230 /// @return A reference to the first element
231 constexpr auto front() noexcept -> T& { return (*this)[0]; }
232
233 /// @brief Get a const-reference to the first element of the array.
234 ///
235 /// @return A reference to the first element
236 constexpr auto front() const noexcept -> T const& { return (*this)[0]; }
237
238 /// @brief Get a const-reference to the last element of the array.
239 ///
240 /// @return A reference to the last element
241 constexpr auto back() noexcept -> T& { return (*this)[N - 1U]; }
242
243 /// @brief Get a const-reference to the last element of the array.
244 ///
245 /// @return A reference to the last element
246 constexpr auto back() const noexcept -> T const& { return (*this)[N - 1U]; }
247
248 // parasoft-begin-suppress AUTOSAR-A11_3_1-a-2 "False positive: It is allowed to declare comparison operators as
249 // friend functions"
250 // parasoft-begin-suppress AUTOSAR-A2_7_3-a-2 "False positive: All overloads are fully are documented"
251 // parasoft-begin-suppress AUTOSAR-A2_7_3-b-2 "False positive: All overloads are fully are documented"
252 // parasoft-begin-suppress AUTOSAR-M3_3_2-a-2 "False positive: cannot apply static here"
253 /// @brief Equality compare all elements in the array.
254 /// @param lhs one of the arrays to compare
255 /// @param rhs the other array to compare
256 /// @return true if all elements in the arrays are equal.
257 /// @return false if any elements in the arrays are not equal, or the sizes of the arrays are different.
258 /// @{
259 template <typename U = T, constraints<std::enable_if_t<is_equality_comparable_v<U>>> = nullptr>
260 friend constexpr auto operator==(array const& lhs, array const& rhs) noexcept -> bool {
261 return arene::base::equal(lhs.begin(), lhs.end(), rhs.begin(), rhs.end());
262 }
263 template <std::size_t UN, typename U = T, constraints<std::enable_if_t<is_equality_comparable_v<U>>> = nullptr>
264 friend constexpr auto operator==(array const&, array<T, UN> const&) noexcept -> bool {
265 return false;
266 }
267 template <
268 typename U = T,
269 constraints<
270 std::enable_if_t<!is_equality_comparable_v<U>>,
271 std::enable_if_t<compare_three_way_supported_v<U>>,
272 std::enable_if_t<!has_fast_inequality_check_v<U>>> = nullptr>
273 friend constexpr auto operator==(array const& lhs, array const& rhs) noexcept -> bool {
274 return array::three_way_compare(lhs, rhs) == arene::base::strong_ordering::equal;
275 }
276 template <
277 typename U = T,
278 constraints<
279 std::enable_if_t<!is_equality_comparable_v<U>>,
280 std::enable_if_t<compare_three_way_supported_v<U>>,
281 std::enable_if_t<has_fast_inequality_check_v<U>>> = nullptr>
282 friend constexpr auto operator==(array const& lhs, array const& rhs) noexcept -> bool {
283 return (array::fast_inequality_check(lhs, rhs) == inequality_heuristic::may_be_equal_or_not_equal) &&
284 (array::three_way_compare(lhs, rhs) == arene::base::strong_ordering::equal);
285 }
286 template <
287 std::size_t UN,
288 typename U = T,
289 constraints<std::enable_if_t<!is_equality_comparable_v<U>>, std::enable_if_t<compare_three_way_supported_v<U>>> =
290 nullptr>
291 friend constexpr auto operator==(array const&, array<T, UN> const&) noexcept -> bool {
292 return false;
293 }
294 /// @}
295 // parasoft-end-suppress AUTOSAR-M3_3_2-a-2
296 // parasoft-end-suppress AUTOSAR-A2_7_3-b-2
297 // parasoft-end-suppress AUTOSAR-A2_7_3-a-2
298 // parasoft-end-suppress AUTOSAR-A11_3_1-a-2
299
300 // parasoft-begin-suppress AUTOSAR-M3_3_2-a-2 "False positive: cannot apply static here"
301 // parasoft-begin-suppress AUTOSAR-A11_3_1-a-2 "False positive: It is allowed to declare comparison operators as
302 // friend functions"
303 // parasoft-begin-suppress CERT_C-EXP37-a-3 "False positive: The rule does not mention naming all parameters"
304 /// @brief Inequality compare all elements in the array.
305 /// @param lhs one of the arrays to compare
306 /// @param rhs the other array to compare
307 /// @return true if any elements in the arrays are not equal, or the sizes of the arrays are different.
308 /// @return false if all elements in the arrays are equal.
309 template <std::size_t UN, typename U = T>
310 friend constexpr auto operator!=(array const& lhs, array<T, UN> const& rhs) noexcept -> bool {
311 return !(lhs == rhs);
312 }
313 // parasoft-end-suppress CERT_C-EXP37-a-3
314 // parasoft-end-suppress AUTOSAR-M3_3_2-a-2
315 // parasoft-end-suppress AUTOSAR-A11_3_1-a-2
316
317 // parasoft-begin-suppress AUTOSAR-A2_10_1-e "False positive: 'three_way_compare' does not hide anything"
318 // parasoft-begin-suppress AUTOSAR-A11_3_1-a-2 "False positive: It is allowed to declare comparison operators as
319 // friend functions"
320 // parasoft-begin-suppress AUTOSAR-A2_7_3-a-2 "False positive: All overloads are fully are documented"
321 // parasoft-begin-suppress AUTOSAR-A2_7_3-b-2 "False positive: All overloads are fully are documented"
322 /// @brief Imparts a lexicographic ordering of two arrays.
323 /// @param lhs one of the arrays to compare
324 /// @param rhs the other array to compare
325 /// @return arene::base::strong_ordering::less if the first element which compares unequal between
326 /// @c rhs and @c lhs also compares less-than, or if @c lhs is a strict prefix of @c rhs.
327 /// @return arene::base::strong_ordering::equal if all elements compare equal.
328 /// @return arene::base::strong_ordering::greater if the first element which compares unequal between
329 /// @c rhs and @c lhs also compares greater, or if @c rhs is a strict prefix of @c lhs.
330 /// @{
331 template <std::size_t UN, typename U = T, constraints<std::enable_if_t<compare_three_way_supported_v<U>>> = nullptr>
332 static constexpr auto three_way_compare(array const& lhs, array<T, UN> const& rhs) noexcept
333 -> arene::base::strong_ordering {
334 return lexicographical_compare_three_way(lhs.begin(), lhs.end(), rhs.begin(), rhs.end());
335 }
336 template <typename U = T, constraints<std::enable_if_t<compare_three_way_supported_v<U>>> = nullptr>
337 static constexpr auto three_way_compare(array const&, array<T, 0> const&) noexcept -> arene::base::strong_ordering {
338 // This overload shouldn't need to exist, but there is a bug in GCC8 where a for-loop over 0 increments results in
339 // the containing function no longer being constexpr.
340 return arene::base::strong_ordering::greater;
341 }
342 /// @}
343 // parasoft-end-suppress AUTOSAR-A2_7_3-b-2
344 // parasoft-end-suppress AUTOSAR-A2_7_3-a-2
345 // parasoft-end-suppress AUTOSAR-A11_3_1-a-2
346 // parasoft-end-suppress AUTOSAR-A2_10_1-e
347
348 // parasoft-begin-suppress AUTOSAR-A2_10_1-e "False positive: 'fast_inequality_check' does not hide anything"
349 /// @brief Quickly checks two arrays for inequality to see if a more costly full ordering check is needed
350 /// @param lhs one of the arrays to compare
351 /// @param rhs the other array to compare
352 /// @return @c arene::base::inequality_heuristic::definitely_not_equal if the two arrays have different sizes or if
353 /// any pair of their elements compare @c definitely_not_equal
354 /// @return @c arene::base::inequality_heuristic::may_be_equal_or_not_equal otherwise
355 template <std::size_t UN, typename U = T, constraints<std::enable_if_t<has_fast_inequality_check_v<U>>> = nullptr>
356 static constexpr auto fast_inequality_check(array const& lhs, array<T, UN> const& rhs) noexcept
357 -> arene::base::inequality_heuristic {
358 if (size() != rhs.size()) {
359 return arene::base::inequality_heuristic::definitely_not_equal;
360 }
361
362 for (size_type idx{}; idx < size(); ++idx) {
363 if (U::fast_inequality_check(lhs[idx], rhs[idx]) == arene::base::inequality_heuristic::definitely_not_equal) {
364 return arene::base::inequality_heuristic::definitely_not_equal;
365 }
366 }
367
368 return arene::base::inequality_heuristic::may_be_equal_or_not_equal;
369 }
370 // parasoft-end-suppress AUTOSAR-A2_10_1-e
371
372 // parasoft-begin-suppress AUTOSAR-A11_3_1-a-2 "False positive: It is allowed to declare comparison operators as
373 // friend functions"
374 // parasoft-begin-suppress AUTOSAR-A2_7_3-a-2 "False positive: All overloads are fully are documented"
375 // parasoft-begin-suppress AUTOSAR-A2_7_3-b-2 "False positive: All overloads are fully are documented"
376 /// @brief Imparts a lexicographic ordering of two arrays.
377 /// @param lhs one of the arrays to compare
378 /// @param rhs the other array to compare
379 /// @see arene::base::array<T,N>::three_way_compare .
380 /// @{
381 template <std::size_t UN>
382 friend constexpr auto operator<(array const& lhs, array<T, UN> const& rhs) noexcept -> bool {
383 return array::three_way_compare(lhs, rhs) == arene::base::strong_ordering::less;
384 }
385 template <std::size_t UN>
386 friend constexpr auto operator<=(array const& lhs, array<T, UN> const& rhs) noexcept -> bool {
387 return array::three_way_compare(lhs, rhs) != arene::base::strong_ordering::greater;
388 }
389 template <std::size_t UN>
390 friend constexpr auto operator>(array const& lhs, array<T, UN> const& rhs) noexcept -> bool {
391 return array::three_way_compare(lhs, rhs) == arene::base::strong_ordering::greater;
392 }
393 template <std::size_t UN>
394 friend constexpr auto operator>=(array const& lhs, array<T, UN> const& rhs) noexcept -> bool {
395 return array::three_way_compare(lhs, rhs) != arene::base::strong_ordering::less;
396 }
397 /// @}
398 // parasoft-end-suppress AUTOSAR-A2_7_3-b-2
399 // parasoft-end-suppress AUTOSAR-A2_7_3-a-2
400 // parasoft-end-suppress AUTOSAR-A11_3_1-a-2
401
402 // parasoft-begin-suppress AUTOSAR-M0_1_8-a-2 "False positive: updates the 'values_' member"
403 /// @brief Set every element in the array to the provided value
404 /// @param val The value to use
405 template <
406 typename U = T,
407 constraints<std::enable_if_t<std::is_same<U, T>::value>, std::enable_if_t<std::is_copy_assignable<U>::value>> =
408 nullptr>
409 constexpr void fill(T const& val) noexcept(std::is_nothrow_copy_assignable<T>::value) {
410 // parasoft-begin-suppress AUTOSAR-A18_1_1-a-2 "This class abstracts over the C array so users don't have to"
411 for (T& elem : values_) {
412 elem = val;
413 }
414 // parasoft-end-suppress AUTOSAR-A18_1_1-a-2
415 }
416 // parasoft-end-suppress AUTOSAR-M0_1_8-a-2
417
418 ///
419 /// @brief swaps all the elements this array and another.
420 ///
421 /// @tparam U the type of the elements in the array. Must satisfy @c is_swappable_v .
422 /// @param other the array to swap elements with
423 /// @post The elements in this array and @c other are exchanged 1:1. Relative order is maintained.
424 ///
425 template <
426 typename U = T,
427 constraints<std::enable_if_t<std::is_same<U, T>::value>, std::enable_if_t<is_swappable_v<U>>> = nullptr>
428 constexpr void swap(array& other) noexcept(is_nothrow_swappable_v<U>) {
429 iterator rhs_iter{other.begin()};
430 for (auto& lhs_elem : *this) {
431 ::arene::base::swap(lhs_elem, *rhs_iter);
432 ++rhs_iter;
433 }
434 }
435
436 // parasoft-begin-suppress AUTOSAR-M3_3_2-a-2 "False positive: cannot apply static here"
437 // parasoft-begin-suppress AUTOSAR-A11_3_1-a-2 "Friend swap operators permitted by A11-3-1 Permit #2 v1.0.0"
438 ///
439 /// @brief swaps all the elements between two arrays.
440 ///
441 /// @tparam U the type of the elements in the array. Must satisfy @c is_swappable_v .
442 /// @param lhs the left hand array to swap.
443 /// @param rhs the right hand array to swap.
444 /// @post The elements in @c lhs and @c rhs are exchanged 1:1. Relative order is maintained.
445 ///
446 template <
447 typename U = T,
448 constraints<std::enable_if_t<std::is_same<U, T>::value>, std::enable_if_t<is_swappable_v<U>>> = nullptr>
449 friend constexpr void swap(array& lhs, array& rhs) noexcept(noexcept(lhs.swap(rhs))) {
450 lhs.swap(rhs);
451 }
452 // parasoft-end-suppress AUTOSAR-A11_3_1-a-2
453 // parasoft-end-suppress AUTOSAR-M3_3_2-a-2
454
455 // parasoft-begin-suppress AUTOSAR-M11_0_1-a-2 "For arene::base::array to match the behaviour of std::array, values_
456 // must be public"
457 // parasoft-begin-suppress AUTOSAR-A18_1_1-a-2 "arene::base::array uses a C-style array so everywhere else can use
458 // arene::base::array instead"
459 /// @brief The actual elements of the @c array object. This must be a public member
460 /// to allow aggregate initialization, but users should treat it as private,
461 /// and only use the documented public interface.
462 // NOLINTNEXTLINE(hicpp-avoid-c-arrays,private-member-variables-in-classes,misc-non-private-member-variables-in-classes,readability-identifier-naming)
463 T values_[N];
464 // parasoft-end-suppress AUTOSAR-M11_0_1-a-2
465 // parasoft-end-suppress AUTOSAR-A18_1_1-a-2
466};
467// parasoft-end-suppress AUTOSAR-A12_1_1-b-2
468// parasoft-end-suppress AUTOSAR-A2_10_1-e
469
470template <typename T, std::size_t N>
471constexpr std::integral_constant<std::size_t, N> array<T, N>::size;
472
473template <typename T, std::size_t N>
474constexpr std::integral_constant<std::size_t, N> array<T, N>::max_size;
475
476template <typename T, std::size_t N>
477constexpr std::integral_constant<bool, false> array<T, N>::empty;
478
479// parasoft-begin-suppress AUTOSAR-A14_7_2-a-2 "False positive: This *is* the same file as the primary template declared
480// above"
481/// @brief Specialize for zero-sized arrays as 'T array[0]' is not standards compliant.
482/// @see arene::base::array
483template <typename T>
484class array<T, 0> {
485 public:
486 /// @brief The type of each array element
487 using value_type = T;
488 /// @brief The type of a pointer to an array element
489 using pointer = T*;
490 /// @brief The type of a pointer to a const array element
491 using const_pointer = T const*;
492 /// @brief The type of a reference to an array element
493 using reference = T&;
494 /// @brief The type of a reference to a const array element
495 using const_reference = T const&;
496 /// @brief The type returned by @c size()
497 using size_type = std::size_t;
498 /// @brief The type for the distance between two iterators
499 using difference_type = std::ptrdiff_t;
500
501 /// @brief An iterator for the array
502 using iterator = typename span<T, 0>::iterator;
503 /// @brief An iterator for the array that treats the elements as @c const
504 using const_iterator = typename span<T const, 0>::iterator;
505
506 /// @brief An iterator for iteration through the array in reverse order.
507 using reverse_iterator = typename span<T, 0>::reverse_iterator;
508 /// @brief An iterator for iteration through the array in reverse order that treats the elements as @c const.
509 using const_reverse_iterator = typename span<T, 0>::const_reverse_iterator;
510
511 // parasoft-begin-suppress AUTOSAR-M11_0_1-a-2 "False positive: this is not 'member data', it is a public property,
512 // exposed as part of the API"
513 /// @brief The number of elements in the array, which is always 0
514 /// @return The size of the array, 0
515 static constexpr std::integral_constant<std::size_t, 0> size{};
516 // parasoft-end-suppress AUTOSAR-M11_0_1-a-2
517
518 // parasoft-begin-suppress AUTOSAR-M11_0_1-a-2 "False positive: this is not 'member data', it is a public property,
519 // exposed as part of the API"
520 /// @brief The maximum number of elements in the array, which is always 0
521 /// @return The size of the array, 0
522 static constexpr std::integral_constant<std::size_t, 0> max_size{};
523 // parasoft-end-suppress AUTOSAR-M11_0_1-a-2
524
525 // parasoft-begin-suppress AUTOSAR-M11_0_1-a-2 "False positive: this is not 'member data', it is a public property,
526 // exposed as part of the API"
527 /// @brief Check if the array is empty, always @c true
528 /// @return true
529 static constexpr std::integral_constant<bool, true> empty{};
530 // parasoft-end-suppress AUTOSAR-M11_0_1-a-2
531
532 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
533 /// @brief Get a pointer to the first element of the array.
534 /// @return A null pointer
535 constexpr auto data() noexcept -> T* { return nullptr; }
536 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
537
538 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
539 /// @brief Get a pointer to the first element of the const array.
540 /// @return A null pointer
541 constexpr auto data() const noexcept -> T const* { return nullptr; }
542 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
543
544 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
545 /// @brief Get an iterator that references the first element of the array.
546 /// @return The iterator
547 constexpr auto begin() noexcept -> iterator { return {}; }
548 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
549
550 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
551 /// @brief Get an iterator that references one-past the last element of the array.
552 /// @return The iterator
553 constexpr auto end() noexcept -> iterator { return {}; }
554 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
555
556 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
557 /// @brief Get a const_iterator that references the first element of the array.
558 /// @return The iterator
559 constexpr auto begin() const noexcept -> const_iterator { return {}; }
560 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
561
562 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
563 /// @brief Get a const_iterator that references one past the last element of the array.
564 /// @return The iterator
565 constexpr auto end() const noexcept -> const_iterator { return {}; }
566 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
567
568 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
569 /// @brief Get an reverse_iterator that references the last element of the array.
570 /// @return The iterator
571 constexpr auto rbegin() noexcept -> reverse_iterator { return {}; }
572 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
573
574 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
575 /// @brief Get an reverse_iterator that references one-before the first element of the array.
576 /// @return The iterator
577 constexpr auto rend() noexcept -> reverse_iterator { return {}; }
578 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
579
580 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
581 /// @brief Get a const_reverse_iterator that references the last element of the array.
582 /// @return The iterator
583 constexpr auto rbegin() const noexcept -> const_reverse_iterator { return {}; }
584 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
585
586 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
587 /// @brief Get a const_reverse_iterator that references one before the first element of the array.
588 /// @return The iterator
589 constexpr auto rend() const noexcept -> const_reverse_iterator { return {}; }
590 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
591
592 /// @brief Get a const_iterator that references the first element of the array.
593 /// @return The iterator
594 static constexpr auto cbegin() noexcept -> const_iterator { return {}; }
595
596 /// @brief Get a const_iterator that references one past the last element of the array.
597 /// @return The iterator
598 static constexpr auto cend() noexcept -> const_iterator { return {}; }
599
600 /// @brief Get a const_reverse_iterator that references the last element of the array.
601 /// @return The iterator
602 static constexpr auto crbegin() noexcept -> const_reverse_iterator { return {}; }
603
604 /// @brief Get a const_reverse_iterator that references one before the first element of the array.
605 /// @return The iterator
606 static constexpr auto crend() noexcept -> const_reverse_iterator { return {}; }
607
608 // parasoft-begin-suppress AUTOSAR-A8_4_2-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
609 // parasoft-begin-suppress CERT_C-MSC37-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
610 // parasoft-begin-suppress CERT_CPP-MSC52-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
611 // parasoft-begin-suppress CERT_C-EXP37-a-3 "False positive: The rule does not mention naming all parameters"
612 // parasoft-begin-suppress AUTOSAR-A2_7_3-a-2 "False positive: All overloads are fully are documented"
613 /// @brief Get a reference to the index'th element of the array.
614 /// @return Never returns
615 ///
616 /// @invariant Will always trigger @c ARENE_PRECONDITION
617 /// @{
618 ARENE_NORETURN constexpr auto operator[](std::size_t) noexcept -> T& {
619 ARENE_PRECONDITION(!empty());
620 ARENE_INVARIANT_UNREACHABLE("Precondition always fires");
621 }
622 ARENE_NORETURN constexpr auto operator[](std::size_t) const noexcept -> T const& {
623 ARENE_PRECONDITION(!empty());
624 ARENE_INVARIANT_UNREACHABLE("Precondition always fires");
625 }
626 /// @}
627 // parasoft-end-suppress AUTOSAR-A2_7_3-a-2
628 // parasoft-end-suppress CERT_C-EXP37-a-3
629 // parasoft-end-suppress CERT_CPP-MSC52-a-2
630 // parasoft-end-suppress CERT_C-MSC37-a-2
631 // parasoft-end-suppress AUTOSAR-A8-4-2-a-2
632
633 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
634 // parasoft-begin-suppress CERT_C-EXP37-a-3 "False positive: The rule does not mention naming all parameters"
635 // parasoft-begin-suppress CERT_C-MSC37-a "False positive: these functions are marked NORETURN."
636 // parasoft-begin-suppress CERT_CPP-MSC52-a "False positive: these functions are marked NORETURN."
637 /// @brief Get a reference to the index'th element of the array.
638 /// @tparam AreExceptionsEnabled Defaulted SFINAE flag to disable this method if exceptions are not enabled; should
639 /// not be specified by user.
640 /// @return Never returns
641 ///
642 /// @throws std::out_of_range unconditionally
643 template <
644 bool AreExceptionsEnabled = detail::are_exceptions_enabled::value,
645 constraints<std::enable_if_t<AreExceptionsEnabled>> = nullptr>
646 ARENE_NORETURN constexpr auto at(std::size_t) -> T& {
647 array_detail::throw_out_of_range();
648 }
649 // parasoft-end-suppress CERT_C-EXP37-a-3
650 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
651
652 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
653 // parasoft-begin-suppress CERT_C-EXP37-a-3 "False positive: The rule does not mention naming all parameters"
654 /// @brief Get a const-reference to the index'th element of the array.
655 /// @tparam AreExceptionsEnabled Defaulted SFINAE flag to disable this method if exceptions are not enabled; should
656 /// not be specified by user.
657 /// @return Never returns
658 ///
659 /// @throws std::out_of_range
660 template <
661 bool AreExceptionsEnabled = detail::are_exceptions_enabled::value,
662 constraints<std::enable_if_t<AreExceptionsEnabled>> = nullptr>
663 ARENE_NORETURN constexpr auto at(std::size_t) const -> T const& {
664 array_detail::throw_out_of_range();
665 }
666 // parasoft-end-suppress CERT_C-EXP37-a-3
667 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
668 // parasoft-begin-suppress CERT_C-MSC37-a
669 // parasoft-begin-suppress CERT_CPP-MSC52-a
670
671 // parasoft-begin-suppress AUTOSAR-A8_4_2-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
672 // parasoft-begin-suppress CERT_C-MSC37-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
673 // parasoft-begin-suppress CERT_CPP-MSC52-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
674 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
675 /// @brief Get a const-reference to the first element of the array.
676 ///
677 /// @return A reference to the first element
678 ARENE_NORETURN constexpr auto front() noexcept -> T& {
679 ARENE_PRECONDITION(!empty());
680 ARENE_INVARIANT_UNREACHABLE("Precondition always fires");
681 }
682 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
683 // parasoft-end-suppress CERT_CPP-MSC52-a-2
684 // parasoft-end-suppress CERT_C-MSC37-a-2
685 // parasoft-end-suppress AUTOSAR-A8-4-2-a-2
686
687 // parasoft-begin-suppress AUTOSAR-A8_4_2-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
688 // parasoft-begin-suppress CERT_C-MSC37-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
689 // parasoft-begin-suppress CERT_CPP-MSC52-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
690 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
691 /// @brief Get a const-reference to the first element of the array.
692 ///
693 /// @return A reference to the first element
694 ARENE_NORETURN constexpr auto front() const noexcept -> T const& {
695 ARENE_PRECONDITION(!empty());
696 ARENE_INVARIANT_UNREACHABLE("Precondition always fires");
697 }
698 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
699 // parasoft-end-suppress CERT_CPP-MSC52-a-2
700 // parasoft-end-suppress CERT_C-MSC37-a-2
701 // parasoft-end-suppress AUTOSAR-A8-4-2-a-2
702
703 // parasoft-begin-suppress AUTOSAR-A8_4_2-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
704 // parasoft-begin-suppress CERT_C-MSC37-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
705 // parasoft-begin-suppress CERT_CPP-MSC52-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
706 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
707 /// @brief Get a const-reference to the last element of the array.
708 ///
709 /// @return A reference to the last element
710 ARENE_NORETURN constexpr auto back() noexcept -> T& {
711 ARENE_PRECONDITION(!empty());
712 ARENE_INVARIANT_UNREACHABLE("Precondition always fires");
713 }
714 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
715 // parasoft-end-suppress CERT_CPP-MSC52-a-2
716 // parasoft-end-suppress CERT_C-MSC37-a-2
717 // parasoft-end-suppress AUTOSAR-A8-4-2-a-2
718
719 // parasoft-begin-suppress AUTOSAR-A8_4_2-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
720 // parasoft-begin-suppress CERT_C-MSC37-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
721 // parasoft-begin-suppress CERT_CPP-MSC52-a-2 "ARENE_PRECONDITION terminates, so does not need a return"
722 // parasoft-begin-suppress AUTOSAR-M9_3_3-a-2 "False positive: 'static' would prevent overloading on 'const'"
723 /// @brief Get a const-reference to the last element of the array.
724 ///
725 /// @return A reference to the last element
726 ARENE_NORETURN constexpr auto back() const noexcept -> T const& {
727 ARENE_PRECONDITION(!empty());
728 ARENE_INVARIANT_UNREACHABLE("Precondition always fires");
729 }
730 // parasoft-end-suppress AUTOSAR-M9_3_3-a-2
731 // parasoft-end-suppress CERT_CPP-MSC52-a-2
732 // parasoft-end-suppress CERT_C-MSC37-a-2
733 // parasoft-end-suppress AUTOSAR-A8-4-2-a-2
734
735 // parasoft-begin-suppress AUTOSAR-M0_1_8-b-2 "Required for consistency with API of primary template"
736 // parasoft-begin-suppress CERT_C-EXP37-a-3 "False positive: The rule does not mention naming all parameters"
737 /// @brief Set every element in the array to the provided value. This is a noop for an empty array.
738 static constexpr void fill(T const&) noexcept {}
739 // parasoft-end-suppress CERT_C-EXP37-a-3
740 // parasoft-end-suppress AUTOSAR-M0_1_8-b-2
741
742 // parasoft-begin-suppress CERT_C-EXP37-a-3 "False positive: The rule does not mention naming all parameters"
743 /// @brief Swap all the elements with another array. This is a noop for an empty array.
744 constexpr void swap(array&) noexcept {}
745 // parasoft-end-suppress CERT_C-EXP37-a-3
746
747 // parasoft-begin-suppress AUTOSAR-A11_3_1-a-2 "Friend swap operators permitted by A11-3-1 Permit #2 v1.0.0"
748 // parasoft-begin-suppress AUTOSAR-A0_1_3-a-2 "False positive: This is a public function, and doesn't need to be used
749 // in the translation unit"
750 /// @brief Swap all the elements with another array. This is a noop for an empty array.
751 friend constexpr void swap(array&, array&) noexcept {}
752 // parasoft-end-suppress AUTOSAR-A0_1_3-a-2
753 // parasoft-end-suppress AUTOSAR-A11_3_1-a-2
754
755 // parasoft-begin-suppress AUTOSAR-A2_7_3-a-2 "False positive: All overloads are fully are documented"
756 // parasoft-begin-suppress AUTOSAR-A2_7_3-b-2 "False positive: All overloads are fully are documented"
757 /// @brief Compares two arrays lexicographically.
758 /// @param lhs The left hand operand to the comparison.
759 /// @param rhs The right hand operand to the comparison.
760 /// @return The equivalent of @c compare_three_way{}(0U,UN)
761 /// @{
762 // parasoft-begin-suppress AUTOSAR-A11_3_1-a-2 "Friend three_way_compare permitted by A11-3-1 Permit #2 v1.0.0""
763 template <std::size_t UN>
764 static constexpr auto three_way_compare(array const&, array<T, UN> const&) noexcept -> arene::base::strong_ordering {
765 return compare_three_way{}(0U, UN);
766 }
767 // parasoft-end-suppress AUTOSAR-A11_3_1-a-2
768 // parasoft-begin-suppress AUTOSAR-A11_3_1-a-2 "False positive: It is allowed to declare comparison operators as
769 // friend functions"
770 template <std::size_t UN>
771 friend constexpr auto operator==(array const& lhs, array<T, UN> const& rhs) noexcept -> bool {
772 return array::three_way_compare(lhs, rhs) == arene::base::strong_ordering::equal;
773 }
774 template <std::size_t UN>
775 friend constexpr auto operator!=(array const& lhs, array<T, UN> const& rhs) noexcept -> bool {
776 return !(lhs == rhs);
777 }
778 template <std::size_t UN>
779 friend constexpr auto operator<(array const& lhs, array<T, UN> const& rhs) noexcept -> bool {
780 return array::three_way_compare(lhs, rhs) == arene::base::strong_ordering::less;
781 }
782 template <std::size_t UN>
783 friend constexpr auto operator<=(array const& lhs, array<T, UN> const& rhs) noexcept -> bool {
784 return array::three_way_compare(lhs, rhs) != arene::base::strong_ordering::greater;
785 }
786 template <std::size_t UN>
787 friend constexpr auto operator>(array const& lhs, array<T, UN> const& rhs) noexcept -> bool {
788 return array::three_way_compare(lhs, rhs) == arene::base::strong_ordering::greater;
789 }
790 template <std::size_t UN>
791 friend constexpr auto operator>=(array const& lhs, array<T, UN> const& rhs) noexcept -> bool {
792 return array::three_way_compare(lhs, rhs) != arene::base::strong_ordering::less;
793 }
794 // parasoft-end-suppress AUTOSAR-A11_3_1-a-2
795 /// @}
796 // parasoft-end-suppress AUTOSAR-A2_7_3-b-2
797 // parasoft-end-suppress AUTOSAR-A2_7_3-a-2
798};
799// parasoft-end-suppress AUTOSAR-A14_7_2-a-2
800
801template <typename T>
802constexpr std::integral_constant<std::size_t, 0> array<T, 0>::size;
803
804template <typename T>
805constexpr std::integral_constant<std::size_t, 0> array<T, 0>::max_size;
806
807template <typename T>
808constexpr std::integral_constant<bool, true> array<T, 0>::empty;
809
810namespace array_detail {
811// parasoft-begin-suppress AUTOSAR-M3_3_2-a-2 "False positive: inline function used in multiple translation units"
812/// @brief Internal function to construct an @c array from a C-style array, using the
813/// specified indices
814/// @tparam T The type of the array elements
815/// @tparam Size The number of array elements
816/// @tparam Indices The indices to use for initialization
817/// @param arr The source array
818/// @return The constructed array
819template <typename T, std::size_t Size, std::size_t... Indices>
820constexpr auto to_array(
821 // NOLINTNEXTLINE(hicpp-avoid-c-arrays)
822 T (&arr)[Size],
823 std::index_sequence<Indices...>
824) noexcept(std::is_nothrow_constructible<base::remove_cvref_t<T>, T&>::value) -> array<base::remove_cvref_t<T>, Size> {
825 return {{arr[Indices]...}};
826}
827// parasoft-end-suppress AUTOSAR-M3_3_2-a-2
828
829// parasoft-begin-suppress AUTOSAR-M3_3_2-a-2 "False positive: inline function used in multiple translation units"
830/// @brief Internal function to construct an @c array from an rvalue C-style array,
831/// using the specified indices
832/// @tparam T The type of the array elements
833/// @tparam Size The number of array elements
834/// @tparam Indices The indices to use for initialization
835/// @param arr The source array
836/// @return The constructed array
837template <typename T, std::size_t Size, std::size_t... Indices>
838constexpr auto to_array(
839 // NOLINTNEXTLINE(hicpp-avoid-c-arrays)
840 T (&&arr)[Size],
841 std::index_sequence<Indices...>
842) noexcept(std::is_nothrow_move_constructible<base::remove_cvref_t<T>>::value) -> array<base::remove_cvref_t<T>, Size> {
843 return {{std::move(arr[Indices])...}};
844}
845// parasoft-end-suppress AUTOSAR-M3_3_2-a-2
846} // namespace array_detail
847
848/// @brief Function to construct an @c array from a C-style array, using the specified
849/// indices
850/// @tparam T The type of the array elements
851/// @tparam Size The number of array elements
852/// @param arr The source array
853/// @return The constructed array
854template <
855 typename T,
856 std::size_t Size,
860// NOLINTNEXTLINE(hicpp-avoid-c-arrays)
865
866// parasoft-begin-suppress AUTOSAR-M3_3_2-a-2 "False positive: inline function used in multiple translation units"
867/// @brief Internal function to construct an @c array from an rvalue C-style array,
868/// using the specified indices
869/// @tparam T The type of the array elements
870/// @tparam Size The number of array elements
871/// @param arr The source array
872/// @return The constructed array
873template <
874 typename T,
875 std::size_t Size,
879// NOLINTNEXTLINE(hicpp-avoid-c-arrays)
884// parasoft-end-suppress AUTOSAR-M3_3_2-a-2
885
886// parasoft-begin-suppress AUTOSAR-M3_3_2-a "False positive: inline function used in multiple translation units"
887
888/// @brief Get a reference to the element at the specified index in the array
889///
890/// @tparam I The index of the element to retrieve. Must satisfy @c I<N .
891/// @tparam T The type of the array elements
892/// @tparam N The number of array elements
893/// @param arr The array to retrieve the element from
894/// @return T& equivalent to @c arr[I] .
895template <std::size_t I, typename T, std::size_t N, constraints<std::enable_if_t<(I < N)>> = nullptr>
896constexpr auto get(array<T, N>& arr) noexcept -> T& {
897 return arr[I];
898}
899/// @brief Get a reference to the element at the specified index in the array
900///
901/// @tparam I The index of the element to retrieve. Must satisfy @c I<N .
902/// @tparam T The type of the array elements
903/// @tparam N The number of array elements
904/// @param arr The array to retrieve the element from
905/// @return T const& equivalent to @c arr[I] .
906template <std::size_t I, typename T, std::size_t N, constraints<std::enable_if_t<(I < N)>> = nullptr>
907constexpr auto get(array<T, N> const& arr) noexcept -> T const& {
908 return arr[I];
909}
910/// @brief Get a reference to the element at the specified index in the array
911///
912/// @tparam I The index of the element to retrieve. Must satisfy @c I<N .
913/// @tparam T The type of the array elements
914/// @tparam N The number of array elements
915/// @param arr The array to retrieve the element from
916/// @return T&& equivalent to @c std::move(arr[I]) .
917template <std::size_t I, typename T, std::size_t N, constraints<std::enable_if_t<(I < N)>> = nullptr>
918constexpr auto get(array<T, N>&& arr) noexcept -> T&& {
919 return std::move(arr[I]);
920}
921/// @brief Get a reference to the element at the specified index in the array
922///
923/// @tparam I The index of the element to retrieve. Must satisfy @c I<N .
924/// @tparam T The type of the array elements
925/// @tparam N The number of array elements
926/// @param arr The array to retrieve the element from
927/// @return T const&& equivalent to @c std::move(arr[I]) .
928template <std::size_t I, typename T, std::size_t N, constraints<std::enable_if_t<(I < N)>> = nullptr>
929constexpr auto get(array<T, N> const&& arr) noexcept -> T const&& {
930 // parasoft-begin-suppress AUTOSAR-A18_9_3-a "Moving is required to maintain rvalue qualification"
931 return std::move(arr[I]);
932 // parasoft-end-suppress AUTOSAR-A18_9_3-a "Moving is required to maintain rvalue qualification"
933}
934
935// parasoft-end-suppress AUTOSAR-M3_3_2-a
936
937} // namespace base
938} // namespace arene
939
940// parasoft-begin-suppress AUTOSAR-A17_6_1-a-2 "False positive: specialization of standard templates is permitted"
941// parasoft-begin-suppress CERT_CPP-DCL58-a-2 "False positive: specialization of standard templates is permitted"
942// parasoft-begin-suppress AUTOSAR-A11_0_2-a "False positive: inheritance from integral_constant is permitted"
943namespace std {
944/// @brief Specialization of @c std::tuple_size for @c arene::base::array
945/// @tparam T The type of the array elements
946/// @tparam N The number of array elements
947template <typename T, std::size_t N>
948class tuple_size<arene::base::array<T, N>> : public std::integral_constant<std::size_t, N> {};
949
950/// @brief Specialization of @c std::tuple_element for @c arene::base::array
951/// @tparam N The index of the element
952/// @tparam T The type of the array elements
953/// @tparam ArrN The number of array elements
954template <std::size_t N, typename T, std::size_t ArrN>
955class tuple_element<N, arene::base::array<T, ArrN>> {
956 static_assert(N < ArrN, "Index out of bounds in std::tuple_element<arene::base::array>");
957
958 public:
959 /// @brief The type of the element at index @c N
960 using type = T;
961};
962
963} // namespace std
964// parasoft-end-suppress AUTOSAR-A11_0_2-a "False positive: inheritance from integral_constant is permitted"
965// parasoft-end-suppress AUTOSAR-A17_6_1-a-2 "False positive: specialization of standard templates is permitted"
966// parasoft-end-suppress CERT_CPP-DCL58-a-2 "False positive: specialization of standard templates is permitted"
967
968// parasoft-end-suppress AUTOSAR-A11_3_1-a-2
969// parasoft-end-suppress AUTOSAR-A13_5_5-b-2
970
971#endif // INCLUDE_GUARD_ARENE_BASE_ARENE_BASE_ARRAY_ARRAY_HPP_
Definition array_exceptions_disabled.cpp:11
Copyright 2026, Toyota Motor Corporation.
Definition array_exceptions_disabled.cpp:10
constexpr auto operator()(::arene::base::result< void, E > const &value) const noexcept(noexcept(hash< E >{}(std::declval< E const & >()))) -> std::size_t
Calculate the hash of a result.
Definition result.hpp:1827