2929#include < mp-units/framework/representation_concepts.h>
3030
3131#if MP_UNITS_HOSTED
32- #include < mp-units/bits/fmt.h>
32+ #include < mp-units/bits/fmt.h>
3333#endif
3434
3535#ifndef MP_UNITS_IN_MODULE_INTERFACE
36- # ifdef MP_UNITS_IMPORT_STD
37- import std;
38- # else
39- # include < cmath>
40- # include < concepts>
41- # include < cstddef>
42- # include < type_traits>
43- # if MP_UNITS_HOSTED
44- # include < ostream>
45- # endif
46- # endif
36+ #ifdef MP_UNITS_IMPORT_STD
37+ import std;
38+ #else
39+ #include < cmath>
40+ #include < concepts>
41+ #include < cstddef>
42+ #include < type_traits>
43+ #if MP_UNITS_HOSTED
44+ #include < ostream>
45+ #endif
46+ #endif
4747#endif
4848
4949namespace mp_units {
@@ -73,13 +73,14 @@ class cartesian_tensor {
7373
7474 // fill ctor (row-major R*C)
7575 template <typename ... Args>
76- requires (sizeof ...(Args) == R * C) && (... && std::constructible_from<T, Args>)
77- constexpr explicit (!(... && std::convertible_to<Args, T>))
78- cartesian_tensor(Args&&... args)
79- : _data_{ static_cast <T>(std::forward<Args>(args))... } {}
76+ requires (sizeof ...(Args) == R * C) && (... && std::constructible_from<T, Args>)
77+ constexpr explicit (!(... && std::convertible_to<Args, T>)) cartesian_tensor(Args&&... args) :
78+ _data_{static_cast <T>(std::forward<Args>(args))...}
79+ {
80+ }
8081
8182 // element access
82- [[nodiscard]] constexpr T& operator ()(std::size_t r, std::size_t c) { return _data_[r * C + c]; }
83+ [[nodiscard]] constexpr T& operator ()(std::size_t r, std::size_t c) { return _data_[r * C + c]; }
8384 [[nodiscard]] constexpr const T& operator ()(std::size_t r, std::size_t c) const { return _data_[r * C + c]; }
8485
8586 // elementwise +, -
@@ -89,8 +90,7 @@ class cartesian_tensor {
8990 {
9091 using CT = std::common_type_t <T, U>;
9192 cartesian_tensor<CT, R, C> Rm{};
92- for (std::size_t i = 0 ; i < R * C; ++i)
93- Rm._data_ [i] = static_cast <CT>(A._data_ [i]) + static_cast <CT>(B._data_ [i]);
93+ for (std::size_t i = 0 ; i < R * C; ++i) Rm._data_ [i] = static_cast <CT>(A._data_ [i]) + static_cast <CT>(B._data_ [i]);
9494 return Rm;
9595 }
9696
@@ -100,15 +100,13 @@ class cartesian_tensor {
100100 {
101101 using CT = std::common_type_t <T, U>;
102102 cartesian_tensor<CT, R, C> Rm{};
103- for (std::size_t i = 0 ; i < R * C; ++i)
104- Rm._data_ [i] = static_cast <CT>(A._data_ [i]) - static_cast <CT>(B._data_ [i]);
103+ for (std::size_t i = 0 ; i < R * C; ++i) Rm._data_ [i] = static_cast <CT>(A._data_ [i]) - static_cast <CT>(B._data_ [i]);
105104 return Rm;
106105 }
107106
108107 // elementwise % (integral uses %, floating uses fmod)
109108 template <typename U>
110- requires (requires (const T& t, const U& u) { t % u; }) ||
111- (std::floating_point<T> && std::floating_point<U>)
109+ requires (requires (const T& t, const U& u) { t % u; }) || (std::floating_point<T> && std::floating_point<U>)
112110 [[nodiscard]] friend constexpr auto operator %(const cartesian_tensor& A, const cartesian_tensor<U, R, C>& B)
113111 {
114112 using CT = std::common_type_t <T, U>;
@@ -117,11 +115,9 @@ class cartesian_tensor {
117115 using std::fmod;
118116 for (std::size_t i = 0 ; i < R * C; ++i)
119117 Rm._data_ [i] =
120- static_cast <CT>(fmod (static_cast <long double >(A._data_ [i]),
121- static_cast <long double >(B._data_ [i])));
118+ static_cast <CT>(fmod (static_cast <long double >(A._data_ [i]), static_cast <long double >(B._data_ [i])));
122119 } else {
123- for (std::size_t i = 0 ; i < R * C; ++i)
124- Rm._data_ [i] = static_cast <CT>(A._data_ [i] % B._data_ [i]);
120+ for (std::size_t i = 0 ; i < R * C; ++i) Rm._data_ [i] = static_cast <CT>(A._data_ [i] % B._data_ [i]);
125121 }
126122 return Rm;
127123 }
@@ -132,8 +128,7 @@ class cartesian_tensor {
132128 {
133129 using CT = std::common_type_t <T, S>;
134130 cartesian_tensor<CT, R, C> Rm{};
135- for (std::size_t i = 0 ; i < R * C; ++i)
136- Rm._data_ [i] = static_cast <CT>(tensor._data_ [i]) * static_cast <CT>(scalar);
131+ for (std::size_t i = 0 ; i < R * C; ++i) Rm._data_ [i] = static_cast <CT>(tensor._data_ [i]) * static_cast <CT>(scalar);
137132 return Rm;
138133 }
139134
@@ -148,8 +143,7 @@ class cartesian_tensor {
148143 {
149144 using CT = std::common_type_t <T, S>;
150145 cartesian_tensor<CT, R, C> Rm{};
151- for (std::size_t i = 0 ; i < R * C; ++i)
152- Rm._data_ [i] = static_cast <CT>(tensor._data_ [i]) / static_cast <CT>(scalar);
146+ for (std::size_t i = 0 ; i < R * C; ++i) Rm._data_ [i] = static_cast <CT>(tensor._data_ [i]) / static_cast <CT>(scalar);
153147 return Rm;
154148 }
155149
@@ -177,71 +171,64 @@ inline constexpr bool is_tensor<cartesian_tensor<T, R, C>> = true;
177171
178172// Matrix × Matrix
179173template <typename T, typename U, std::size_t R, std::size_t K, std::size_t C>
180- [[nodiscard]] constexpr auto matmul (const cartesian_tensor<T, R, K>& A,
181- const cartesian_tensor<U, K, C>& B)
174+ [[nodiscard]] constexpr auto matmul (const cartesian_tensor<T, R, K>& A, const cartesian_tensor<U, K, C>& B)
182175{
183176 using CT = std::common_type_t <T, U>;
184177 cartesian_tensor<CT, R, C> Rm{};
185178 for (std::size_t r = 0 ; r < R; ++r)
186179 for (std::size_t c = 0 ; c < C; ++c) {
187180 CT acc{};
188- for (std::size_t k = 0 ; k < K; ++k)
189- acc += static_cast <CT>(A (r, k)) * static_cast <CT>(B (k, c));
181+ for (std::size_t k = 0 ; k < K; ++k) acc += static_cast <CT>(A (r, k)) * static_cast <CT>(B (k, c));
190182 Rm (r, c) = acc;
191183 }
192184 return Rm;
193185}
194186
195187// Matrix × Vector (3×3)
196188template <typename T, typename U>
197- [[nodiscard]] constexpr auto matvec (const cartesian_tensor<T, 3 , 3 >& M,
198- const cartesian_vector<U>& x)
189+ [[nodiscard]] constexpr auto matvec (const cartesian_tensor<T, 3 , 3 >& M, const cartesian_vector<U>& x)
199190{
200191 using CT = std::common_type_t <T, U>;
201192 cartesian_vector<CT> y{};
202193 for (std::size_t r = 0 ; r < 3 ; ++r) {
203194 CT acc{};
204- for (std::size_t c = 0 ; c < 3 ; ++c)
205- acc += static_cast <CT>(M (r, c)) * static_cast <CT>(x[c]);
195+ for (std::size_t c = 0 ; c < 3 ; ++c) acc += static_cast <CT>(M (r, c)) * static_cast <CT>(x[c]);
206196 y[r] = acc;
207197 }
208198 return y;
209199}
210200
211201// Double contraction: A : B
212202template <typename T, typename U, std::size_t R, std::size_t C>
213- [[nodiscard]] constexpr auto double_contraction (const cartesian_tensor<T, R, C>& A,
214- const cartesian_tensor<U, R, C>& B)
203+ [[nodiscard]] constexpr auto double_contraction (const cartesian_tensor<T, R, C>& A, const cartesian_tensor<U, R, C>& B)
215204{
216205 using CT = std::common_type_t <T, U>;
217206 CT acc{};
218- for (std::size_t i = 0 ; i < R * C; ++i)
219- acc += static_cast <CT>(A._data_ [i]) * static_cast <CT>(B._data_ [i]);
207+ for (std::size_t i = 0 ; i < R * C; ++i) acc += static_cast <CT>(A._data_ [i]) * static_cast <CT>(B._data_ [i]);
220208 return acc; // numeric scalar
221209}
222210
223211// Outer product: vector ⊗ vector -> 3x3 matrix
224212template <typename T, typename U>
225- [[nodiscard]] constexpr auto outer_numeric (const cartesian_vector<T>& a,
226- const cartesian_vector<U>& b)
213+ [[nodiscard]] constexpr auto outer_numeric (const cartesian_vector<T>& a, const cartesian_vector<U>& b)
227214{
228215 using CT = std::common_type_t <T, U>;
229216 cartesian_tensor<CT, 3 , 3 > Rm{};
230217 for (std::size_t i = 0 ; i < 3 ; ++i)
231- for (std::size_t j = 0 ; j < 3 ; ++j)
232- Rm (i, j) = static_cast <CT>(a[i]) * static_cast <CT>(b[j]);
218+ for (std::size_t j = 0 ; j < 3 ; ++j) Rm (i, j) = static_cast <CT>(a[i]) * static_cast <CT>(b[j]);
233219 return Rm;
234220}
235221
236- } // namespace mp_units
222+ } // namespace mp_units
237223
238224#if MP_UNITS_HOSTED
239225// fmt/format (or std::format) support
240226template <typename T, std::size_t R, std::size_t C, typename Char>
241- struct MP_UNITS_STD_FMT ::formatter<mp_units::cartesian_tensor<T, R, C>, Char>
242- : formatter<std::basic_string_view<Char>, Char> {
227+ struct MP_UNITS_STD_FMT ::formatter<mp_units::cartesian_tensor<T, R, C>, Char> :
228+ formatter<std::basic_string_view<Char>, Char> {
243229 template <typename Ctx>
244- auto format (const mp_units::cartesian_tensor<T, R, C>& A, Ctx& ctx) const {
230+ auto format (const mp_units::cartesian_tensor<T, R, C>& A, Ctx& ctx) const
231+ {
245232 auto out = ctx.out ();
246233 for (std::size_t r = 0 ; r < R; ++r) {
247234 out = format_to (out, " {}" , (r == 0 ? " [[" : " [" ));
0 commit comments