Arene Base
Fundamental Utilities For Safety Critical C++
Loading...
Searching...
No Matches
explicit_base_set.hpp
Go to the documentation of this file.
1// parasoft-begin-suppress AUTOSAR-A2_8_1-a "False positive: also defines arene::base::units_detail::explicit_base_set"
2#ifndef INCLUDE_GUARD_ARENE_BASE_ARENE_BASE_UNITS_EXPLICIT_BASE_SET_HPP_
3#define INCLUDE_GUARD_ARENE_BASE_ARENE_BASE_UNITS_EXPLICIT_BASE_SET_HPP_
4
5#include "arene/base/constraints/constraints.hpp"
6#include "arene/base/stdlib_choice/cstddef.hpp"
7#include "arene/base/stdlib_choice/enable_if.hpp"
8#include "arene/base/stdlib_choice/remove_const.hpp"
9#include "arene/base/stdlib_choice/remove_cv.hpp"
10#include "arene/base/type_traits/always_false.hpp"
11#include "arene/base/units/base_kind_set.hpp"
12#include "arene/base/units/is_explicit.hpp"
13#include "arene/base/units/is_quantity_kind.hpp"
14#include "arene/base/units/kind_with_exponent_fwd.hpp"
15#include "arene/base/units/quantity_kind.hpp"
16#include "arene/base/units/scaled_unit.hpp"
17
18// parasoft-begin-suppress AUTOSAR-A7_1_5-a-2 "Trailing return syntax permitted by A7-1-5 Permit #1 v1.0.0"
19// parasoft-begin-suppress AUTOSAR-A3_1_5-a "False positive: all functions are constexpr so are intended to be inlined"
20// parasoft-begin-suppress AUTOSAR-M2_10_1-a "Similar identifiers permitted by M2-10-1 Permit #1 v1.0.0"
21
22namespace arene {
23namespace base {
24
25namespace combine_kinds_detail {
26/// @brief A template that represents a quantity kind that is a combination of base quantity kinds
27/// @tparam BaseKinds The base quantity kinds to combine
28template <typename... BaseKinds>
29class combined_quantity_kind;
30} // namespace combine_kinds_detail
31
32namespace units_detail {
33
34/// @brief provide a barrier type to treat a quantity kind as explicit
35/// @tparam Kind quantity kind type
36///
37/// Creates a quantity kind barrier, blocking rules for implicit kinds when
38/// determining the explicit base set.
39template <typename Kind>
40class explicit_base_barrier : public quantity_kind<explicit_base_barrier<Kind>> {};
41
42namespace explicit_base_set_detail {
43
44/// @brief helper used to denote that the explicit base set cannot be determined
45/// for the specified type
46/// @tparam Kind quantity kind of which to obtain the explicit base set
47/// @return never actually returns as use of this function is always a
48/// compilation error.
49template <typename Kind>
50constexpr auto explicit_base_set_error() -> std::nullptr_t {
51 static_assert( //
52 is_quantity_kind_v<Kind>,
53 "explicit base set cannot be determined for invalid quantity kind"
54 );
55 static_assert(
56 always_false_v<Kind>,
57 "internal error: a valid quantity kind was sorted to the explicit_base_set_error function by mistake"
58 );
59 return {};
60}
61
62/// @brief obtains the explicit base set of a quantity kind
63/// @tparam Kind quantity kind of which to obtain the explicit base set
64///
65/// This primary template is always an error.
66template <typename Kind, typename = constraints<>>
67extern constexpr auto explicit_base_set = explicit_base_set_error<Kind>();
68
69/// @brief obtains the explicit base set of a quantity kind
70/// @tparam Kind quantity kind of which to obtain the explicit base set
71///
72/// This specialization handles an explicit quantity kind.
73template <typename Kind>
74extern constexpr auto explicit_base_set<Kind, constraints<std::enable_if_t<is_explicit_v<Kind>>>> =
75 base_kind_set<Kind>{base_kind_exponents{1U, 0U}};
76
77// scaled unit not yet handled
78
79/// @brief obtains the explicit base set of a quantity kind
80/// @tparam Kind quantity kind of which to obtain the explicit base set
81///
82/// This specialization handles an quantity kind with exponent.
83template <typename Kind, exponent_t PositiveExponent, exponent_t NegativeExponent>
84extern constexpr auto
85 explicit_base_set<quantity_kind_with_exponent<Kind, PositiveExponent, NegativeExponent, constraints<>>> = //
86 set_union( //
87 PositiveExponent * explicit_base_set<typename Kind::quantity_kind_type>, //
88 -NegativeExponent* explicit_base_set<typename Kind::quantity_kind_type> //
89 );
90
91/// @brief obtains the explicit base set of a quantity kind
92/// @tparam Kind quantity kind of which to obtain the explicit base set
93///
94/// This specialization handles a combined quantity kind.
95template <typename... BaseKinds>
96extern constexpr auto explicit_base_set<combine_kinds_detail::combined_quantity_kind<BaseKinds...>> =
97 set_union(explicit_base_set<BaseKinds>...);
98
99/// @brief obtains the explicit base set of a quantity kind
100/// @tparam BaseUnit the base unit for the scaled unit
101/// @tparam Scale the scale factor for the scaled unit
102///
103/// This specialization handles a scaled quantity kind.
104template <typename BaseUnit, typename Scale>
105extern constexpr auto explicit_base_set<scaled_unit_detail::scaled_unit_impl<BaseUnit, Scale>> =
106 explicit_base_set<BaseUnit>;
107
108} // namespace explicit_base_set_detail
109
110/// @brief obtains the explicit base set of a quantity kind
111/// @tparam Kind quantity kind of which to obtain the explicit base set
112///
113/// Obtains a set of elements specifying the explicit base set of a quantity
114/// kind. Each set element is a triple of <c>(Kind, PositiveExponent,
115/// NegativeExponent)</c>.
116///
117/// * If @c Kind is an explicit quantity kind, this set is <c>{(Kind, 1,
118/// 0)}</c>.
119/// * otherwise, if @c Kind is a scaled unit, this set is the explict base set
120/// for the base unit of @c Kind.
121/// * otherwise, if @c Kind is a composite quantity kind consisting of @c I
122/// quantity kinds @c Ki with explicit base sets @c E(K_ij) equal to <c>{(K_ij,
123/// P_ij, N_ij)}</c>, then the explicit base set of @c Kind is the set <c>{(K_n,
124/// P_n, N_n)}</c> where the quantity kinds @c K_n are the distinct quantity
125/// kinds from @c K_ij, and @c P_n is the sum of the corresponding positive
126/// exponents <c>P_i * P_ij + N_i * N_ij</c>, @c N_n is the sum of the
127/// corresponding negative exponents <c>N_i * P_ij + P_i * N_ij</c>, where
128/// @c P_i and @c N_i are the positive and negative exponents of @c K_i
129/// * otherwise, there is an error.
130///
131template <typename Kind>
132extern constexpr auto explicit_base_set = explicit_base_set_detail::explicit_base_set<std::remove_cv_t<Kind>>;
133
134/// @brief trait to obtain the type of the explicit base set of a quantity kind
135/// @tparam Kind quantity kind of which to obtain the explicit base set
136template <typename Kind>
137using explicit_base_set_t = std::remove_const_t<decltype(explicit_base_set<Kind>)>;
138
139} // namespace units_detail
140
141} // namespace base
142} // namespace arene
143
144#endif // INCLUDE_GUARD_ARENE_BASE_ARENE_BASE_UNITS_EXPLICIT_BASE_SET_HPP_
Definition array_exceptions_disabled.cpp:11
Copyright 2026, Toyota Motor Corporation.
Definition array_exceptions_disabled.cpp:10