44 * Copyright (c) 2011-2012, 2014-2015, Niklas Hauser
55 * Copyright (c) 2015, Sascha Schade
66 * Copyright (c) 2020, Christopher Durand
7+ * Copyright (c) 2021, Thomas Sommer
78 *
89 * This file is part of the modm project.
910 *
1617#ifndef MODM_MATH_UTILS_MISC_HPP
1718#define MODM_MATH_UTILS_MISC_HPP
1819
19- #include < cstddef>
20- #include < cmath>
2120#include < stdint.h>
21+
22+ #include < cmath>
23+ #include < cstddef>
2224#include < type_traits>
25+ #include < utility>
2326
2427#include < modm/architecture/utils.hpp>
2528
@@ -60,65 +63,53 @@ pow(uint32_t base, uint8_t exponent)
6063}
6164
6265/* *
63- * @brief This does what you think it does.
66+ * @brief Variadic min for 2-∞ objects
6467 *
65- * @param a A thing of arbitrary type.
66- * @param b Another thing of arbitrary type.
67- * @return The lesser of the parameters.
68+ * @param a first object to compare
69+ * @param b second object to compare
70+ * @param cs Further objects for comparison
6871 *
69- * This is the simple classic generic implementation. It will work on
70- * temporary expressions, since they are only evaluated once, unlike a
71- * preprocessor macro.
72+ * @return The smallest object
73+ *
74+ * @see https://stackoverflow.com/questions/23815138/implementing-variadic-min-max-functions
7275 */
7376template <typename T>
74- inline const T&
75- min (const T& a, const T& b)
77+ constexpr T vmin (T a, T b)
7678{
77- if (b < a)
78- return b;
79- else
80- return a;
79+ return a < b ? a : b;
8180}
8281
83- /* *
84- * @brief This does what you think it does.
85- *
86- * @param a A thing of arbitrary type.
87- * @param b Another thing of arbitrary type.
88- * @return The greater of the parameters.
89- *
90- * This is the simple classic generic implementation. It will work on
91- * temporary expressions, since they are only evaluated once, unlike a
92- * preprocessor macro.
93- */
94- template <typename T>
95- inline const T&
96- max (const T& a, const T& b)
82+ template <typename T, typename ... Ts>
83+ constexpr T vmin (T a, T b, Ts&&... cs)
9784{
98- if (a < b)
99- return b;
100- else
101- return a;
85+ return a < b ?
86+ vmin (a, std::forward<Ts>(cs)...) :
87+ vmin (b, std::forward<Ts>(cs)...);
10288}
10389
10490/* *
105- * @brief This does what you think it does.
91+ * @brief Variadic max for 2-∞ objects
10692 *
107- * @param a A thing of arbitrary type.
108- * @param b Another thing of arbitrary type.
109- * @param c Something else of arbitrary type.
110- * @return The greater of the three parameters.
93+ * @param a first object to compare
94+ * @param b second object to compare
95+ * @param cs Further objects for comparison
96+ *
97+ * @return The biggest object
11198 *
112- * This is the simple classic generic implementation. It will work on
113- * temporary expressions, since they are only evaluated once, unlike a
114- * preprocessor macro.
99+ * @see https://stackoverflow.com/questions/23815138/implementing-variadic-min-max-functions
115100 */
116101template <typename T>
117- constexpr T
118- max (const T a, const T b, const T c)
102+ constexpr T vmax (T& a, T& b)
103+ {
104+ return a > b ? a : b;
105+ }
106+
107+ template <typename T, typename ... Ts>
108+ constexpr T vmax (T& a, T& b, Ts&... cs)
119109{
120- return ( ( (b > c) ? b : c ) > a ) ?
121- ( (b > c) ? b : c) : a;
110+ return a > b ?
111+ vmax (a, std::forward<Ts>(cs)...) :
112+ vmax (b, std::forward<Ts>(cs)...);
122113}
123114
124115/* *
@@ -136,10 +127,7 @@ template<typename T, typename Compare>
136127inline const T&
137128min (const T& a, const T& b, Compare compare)
138129{
139- if (compare (b, a))
140- return b;
141- else
142- return a;
130+ return compare (b, a) ? b : a;
143131}
144132
145133/* *
@@ -157,24 +145,16 @@ template<typename T, typename Compare>
157145inline const T&
158146max (const T& a, const T& b, Compare compare)
159147{
160- if (compare (a, b))
161- return b;
162- else
163- return a;
148+ return compare (a, b) ? b : a;
164149}
165150
166151/* *
167152 * @brief constexpr implementation of fabs
168153 */
169- template <typename Float>
170- requires std::is_floating_point_v<Float>
154+ template <std::floating_point Float>
171155constexpr Float constexpr_fabs (Float number)
172156{
173- if (number >= 0 ) {
174- return number;
175- } else {
176- return -number;
177- }
157+ return number >= 0 ? number : -number;
178158}
179159
180160// / @}
0 commit comments