diff --git a/src/core/include/mp-units/bits/quantity_cast.h b/src/core/include/mp-units/bits/quantity_cast.h index 4fa7d08b..93954da2 100644 --- a/src/core/include/mp-units/bits/quantity_cast.h +++ b/src/core/include/mp-units/bits/quantity_cast.h @@ -51,9 +51,9 @@ template { if constexpr (detail::QuantityKindSpec> && AssociatedUnit>) - return make_quantity(std::forward(q).numerical_value_); + return make_quantity(std::forward(q).numerical_value_is_an_implementation_detail_); else - return make_quantity{}>(std::forward(q).numerical_value_); + return make_quantity{}>(std::forward(q).numerical_value_is_an_implementation_detail_); } } // namespace mp_units diff --git a/src/core/include/mp-units/bits/sudo_cast.h b/src/core/include/mp-units/bits/sudo_cast.h index 891b680f..bdc4f67e 100644 --- a/src/core/include/mp-units/bits/sudo_cast.h +++ b/src/core/include/mp-units/bits/sudo_cast.h @@ -63,10 +63,11 @@ template if constexpr (q_unit == To::unit) { // no scaling of the number needed return make_quantity(static_cast( - std::forward(q).numerical_value_)); // this is the only (and recommended) way to do - // a truncating conversion on a number, so we are - // using static_cast to suppress all the compiler - // warnings on conversions + std::forward(q) + .numerical_value_is_an_implementation_detail_)); // this is the only (and recommended) way to do + // a truncating conversion on a number, so we are + // using static_cast to suppress all the compiler + // warnings on conversions } else { // scale the number constexpr Magnitude auto c_mag = get_canonical_unit(q_unit).mag / get_canonical_unit(To::unit).mag; @@ -78,8 +79,9 @@ template using multiplier_type = conditional, std::common_type_t, c_mag_type>; constexpr auto val = [](Magnitude auto m) { return get_value(m); }; - return static_cast(static_cast(std::forward(q).numerical_value_) * - val(num) / val(den) * val(irr)) * + return static_cast( + static_cast(std::forward(q).numerical_value_is_an_implementation_detail_) * val(num) / + val(den) * val(irr)) * To::reference; } } diff --git a/src/core/include/mp-units/quantity.h b/src/core/include/mp-units/quantity.h index 2ebc1edd..3537fddb 100644 --- a/src/core/include/mp-units/quantity.h +++ b/src/core/include/mp-units/quantity.h @@ -85,7 +85,7 @@ using common_quantity_for = quantity Rep = double> class quantity { public: - Rep numerical_value_; // needs to be public for a structural type + Rep numerical_value_is_an_implementation_detail_; // needs to be public for a structural type // member types and values static constexpr Reference auto reference = R; @@ -126,7 +126,8 @@ public: template Q> constexpr explicit(!std::convertible_to) quantity(const Q& q) : - numerical_value_(detail::sudo_cast(q).numerical_value_) + numerical_value_is_an_implementation_detail_( + detail::sudo_cast(q).numerical_value_is_an_implementation_detail_) { } @@ -163,14 +164,14 @@ public: requires(U{} == unit) [[nodiscard]] constexpr rep& numerical_value_ref_in(U) & noexcept { - return numerical_value_; + return numerical_value_is_an_implementation_detail_; } template requires(U{} == unit) [[nodiscard]] constexpr const rep& numerical_value_ref_in(U) const& noexcept { - return numerical_value_; + return numerical_value_is_an_implementation_detail_; } template @@ -181,39 +182,43 @@ public: requires requires(quantity q) { q.in(U{}); } [[nodiscard]] constexpr rep numerical_value_in(U) const noexcept { - return (*this).in(U{}).numerical_value_; + return (*this).in(U{}).numerical_value_is_an_implementation_detail_; } template U> requires requires(quantity q) { q.force_in(U{}); } [[nodiscard]] constexpr rep force_numerical_value_in(U) const noexcept { - return (*this).force_in(U{}).numerical_value_; + return (*this).force_in(U{}).numerical_value_is_an_implementation_detail_; } // conversion operators template> requires detail::QuantityConvertibleTo< quantity, quantity::reference, typename quantity_like_traits::rep>> - [[nodiscard]] explicit(is_specialization_of::from_numerical_value(numerical_value_)), + [[nodiscard]] explicit(is_specialization_of::from_numerical_value( + numerical_value_is_an_implementation_detail_)), convert_explicitly> || !std::convertible_to) constexpr - operator Q_() const& noexcept(noexcept(quantity_like_traits::from_numerical_value(numerical_value_)) && - std::is_nothrow_copy_constructible_v) + operator Q_() const& noexcept( + noexcept(quantity_like_traits::from_numerical_value(numerical_value_is_an_implementation_detail_)) && + std::is_nothrow_copy_constructible_v) { - return quantity_like_traits::from_numerical_value(numerical_value_).value; + return quantity_like_traits::from_numerical_value(numerical_value_is_an_implementation_detail_).value; } template> requires detail::QuantityConvertibleTo< quantity, quantity::reference, typename quantity_like_traits::rep>> - [[nodiscard]] explicit(is_specialization_of::from_numerical_value(numerical_value_)), + [[nodiscard]] explicit(is_specialization_of::from_numerical_value( + numerical_value_is_an_implementation_detail_)), convert_explicitly> || !std::convertible_to) constexpr - operator Q_() && noexcept(noexcept(quantity_like_traits::from_numerical_value(numerical_value_)) && - std::is_nothrow_move_constructible_v) + operator Q_() && noexcept( + noexcept(quantity_like_traits::from_numerical_value(numerical_value_is_an_implementation_detail_)) && + std::is_nothrow_move_constructible_v) { - return quantity_like_traits::from_numerical_value(std::move(numerical_value_)).value; + return quantity_like_traits::from_numerical_value(std::move(numerical_value_is_an_implementation_detail_)).value; } // member unary operators @@ -224,7 +229,7 @@ public: } -> std::common_with; } { - return make_quantity(+numerical_value_); + return make_quantity(+numerical_value_is_an_implementation_detail_); } [[nodiscard]] constexpr Quantity auto operator-() const @@ -234,7 +239,7 @@ public: } -> std::common_with; } { - return make_quantity(-numerical_value_); + return make_quantity(-numerical_value_is_an_implementation_detail_); } template @@ -245,7 +250,7 @@ public: } -> std::same_as; } { - ++q.numerical_value_; + ++q.numerical_value_is_an_implementation_detail_; return std::forward(q); } @@ -256,7 +261,7 @@ public: } -> std::common_with; } { - return make_quantity(numerical_value_++); + return make_quantity(numerical_value_is_an_implementation_detail_++); } template @@ -267,7 +272,7 @@ public: } -> std::same_as; } { - --q.numerical_value_; + --q.numerical_value_is_an_implementation_detail_; return std::forward(q); } @@ -278,7 +283,7 @@ public: } -> std::common_with; } { - return make_quantity(numerical_value_--); + return make_quantity(numerical_value_is_an_implementation_detail_--); } // compound assignment operators @@ -290,7 +295,7 @@ public: } friend constexpr decltype(auto) operator+=(Q&& lhs, const quantity& rhs) { - lhs.numerical_value_ += rhs.numerical_value_; + lhs.numerical_value_is_an_implementation_detail_ += rhs.numerical_value_is_an_implementation_detail_; return std::forward(lhs); } @@ -302,7 +307,7 @@ public: } friend constexpr decltype(auto) operator-=(Q&& lhs, const quantity& rhs) { - lhs.numerical_value_ -= rhs.numerical_value_; + lhs.numerical_value_is_an_implementation_detail_ -= rhs.numerical_value_is_an_implementation_detail_; return std::forward(lhs); } @@ -317,7 +322,7 @@ public: { gsl_ExpectsAudit(rhs != zero()); - lhs.numerical_value_ %= rhs.numerical_value_; + lhs.numerical_value_is_an_implementation_detail_ %= rhs.numerical_value_is_an_implementation_detail_; return std::forward(lhs); } @@ -330,7 +335,7 @@ public: } friend constexpr decltype(auto) operator*=(Q&& lhs, const Value& v) { - lhs.numerical_value_ *= v; + lhs.numerical_value_is_an_implementation_detail_ *= v; return std::forward(lhs); } @@ -343,7 +348,7 @@ public: } friend constexpr decltype(auto) operator*=(Q1&& lhs, const Q2& rhs) { - lhs.numerical_value_ *= rhs.numerical_value_; + lhs.numerical_value_is_an_implementation_detail_ *= rhs.numerical_value_is_an_implementation_detail_; return std::forward(lhs); } @@ -357,7 +362,7 @@ public: friend constexpr decltype(auto) operator/=(Q&& lhs, const Value& v) { gsl_ExpectsAudit(v != quantity_values::zero()); - lhs.numerical_value_ /= v; + lhs.numerical_value_is_an_implementation_detail_ /= v; return std::forward(lhs); } @@ -371,7 +376,7 @@ public: friend constexpr decltype(auto) operator/=(Q1&& lhs, const Q2& rhs) { gsl_ExpectsAudit(rhs != rhs.zero()); - lhs.numerical_value_ /= rhs.numerical_value_; + lhs.numerical_value_is_an_implementation_detail_ /= rhs.numerical_value_is_an_implementation_detail_; return std::forward(lhs); } @@ -385,7 +390,7 @@ private: template requires std::constructible_from - constexpr explicit quantity(Value&& v) : numerical_value_(std::forward(v)) + constexpr explicit quantity(Value&& v) : numerical_value_is_an_implementation_detail_(std::forward(v)) { } }; @@ -402,7 +407,10 @@ template [[nodiscard]] constexpr Quantity auto operator+(const quantity& lhs, const quantity& rhs) { using ret = detail::common_quantity_for, quantity, quantity>; - return make_quantity(ret(lhs).numerical_value_ + ret(rhs).numerical_value_); + const ret ret_lhs(lhs); + const ret ret_rhs(rhs); + return make_quantity(ret_lhs.numerical_value_ref_in(ret::unit) + + ret_rhs.numerical_value_ref_in(ret::unit)); } template @@ -410,7 +418,10 @@ template [[nodiscard]] constexpr Quantity auto operator-(const quantity& lhs, const quantity& rhs) { using ret = detail::common_quantity_for, quantity, quantity>; - return make_quantity(ret(lhs).numerical_value_ - ret(rhs).numerical_value_); + const ret ret_lhs(lhs); + const ret ret_rhs(rhs); + return make_quantity(ret_lhs.numerical_value_ref_in(ret::unit) - + ret_rhs.numerical_value_ref_in(ret::unit)); } template @@ -420,7 +431,10 @@ template { gsl_ExpectsAudit(rhs != rhs.zero()); using ret = detail::common_quantity_for, quantity, quantity>; - return make_quantity(ret(lhs).numerical_value_ % ret(rhs).numerical_value_); + const ret ret_lhs(lhs); + const ret ret_rhs(rhs); + return make_quantity(ret_lhs.numerical_value_ref_in(ret::unit) % + ret_rhs.numerical_value_ref_in(ret::unit)); } template @@ -428,7 +442,8 @@ template Rep2> [[nodiscard]] constexpr Quantity auto operator*(const quantity& lhs, const quantity& rhs) { - return make_quantity(lhs.numerical_value_ * rhs.numerical_value_); + return make_quantity(lhs.numerical_value_ref_in(quantity::unit) * + rhs.numerical_value_ref_in(quantity::unit)); } template @@ -436,7 +451,7 @@ template detail::InvokeResultOf, Rep, const Value&> [[nodiscard]] constexpr Quantity auto operator*(const quantity& q, const Value& v) { - return make_quantity(q.numerical_value_ * v); + return make_quantity(q.numerical_value_ref_in(quantity::unit) * v); } template @@ -444,7 +459,7 @@ template detail::InvokeResultOf, const Value&, Rep> [[nodiscard]] constexpr Quantity auto operator*(const Value& v, const quantity& q) { - return make_quantity(v * q.numerical_value_); + return make_quantity(v * q.numerical_value_ref_in(quantity::unit)); } template @@ -452,7 +467,8 @@ template [[nodiscard]] constexpr Quantity auto operator/(const quantity& lhs, const quantity& rhs) { gsl_ExpectsAudit(rhs != rhs.zero()); - return make_quantity(lhs.numerical_value_ / rhs.numerical_value_); + return make_quantity(lhs.numerical_value_ref_in(quantity::unit) / + rhs.numerical_value_ref_in(quantity::unit)); } template @@ -461,7 +477,7 @@ template [[nodiscard]] constexpr Quantity auto operator/(const quantity& q, const Value& v) { gsl_ExpectsAudit(v != quantity_values::zero()); - return make_quantity(q.numerical_value_ / v); + return make_quantity(q.numerical_value_ref_in(quantity::unit) / v); } template @@ -469,7 +485,7 @@ template detail::InvokeResultOf, const Value&, Rep> [[nodiscard]] constexpr Quantity auto operator/(const Value& v, const quantity& q) { - return make_quantity<::mp_units::one / R>(v / q.numerical_value_); + return make_quantity<::mp_units::one / R>(v / q.numerical_value_ref_in(quantity::unit)); } template @@ -478,7 +494,9 @@ template [[nodiscard]] constexpr bool operator==(const quantity& lhs, const quantity& rhs) { using ct = std::common_type_t, quantity>; - return ct(lhs).numerical_value_ == ct(rhs).numerical_value_; + const ct ct_lhs(lhs); + const ct ct_rhs(rhs); + return ct_lhs.numerical_value_ref_in(ct::unit) == ct_rhs.numerical_value_ref_in(ct::unit); } template @@ -487,7 +505,9 @@ template [[nodiscard]] constexpr auto operator<=>(const quantity& lhs, const quantity& rhs) { using ct = std::common_type_t, quantity>; - return ct(lhs).numerical_value_ <=> ct(rhs).numerical_value_; + const ct ct_lhs(lhs); + const ct ct_rhs(rhs); + return ct_lhs.numerical_value_ref_in(ct::unit) <=> ct_rhs.numerical_value_ref_in(ct::unit); } // make_quantity diff --git a/src/core/include/mp-units/quantity_spec.h b/src/core/include/mp-units/quantity_spec.h index 37de04d9..900362dd 100644 --- a/src/core/include/mp-units/quantity_spec.h +++ b/src/core/include/mp-units/quantity_spec.h @@ -119,7 +119,8 @@ struct quantity_spec_interface { requires Quantity> && (explicitly_convertible(std::remove_reference_t::quantity_spec, self)) { - return make_quantity::unit>{}>(std::forward(q).numerical_value_); + return make_quantity::unit>{}>( + std::forward(q).numerical_value_is_an_implementation_detail_); } #else template U> @@ -133,7 +134,8 @@ struct quantity_spec_interface { (explicitly_convertible(std::remove_reference_t::quantity_spec, Self_{})) [[nodiscard]] constexpr Quantity auto operator()(Q&& q) const { - return make_quantity::unit>{}>(std::forward(q).numerical_value_); + return make_quantity::unit>{}>( + std::forward(q).numerical_value_is_an_implementation_detail_); } #endif }; @@ -309,7 +311,8 @@ struct quantity_spec : std::remove_const_t { (explicitly_convertible(std::remove_reference_t::quantity_spec, Self_{})) [[nodiscard]] constexpr Quantity auto operator()(Q&& q) const { - return make_quantity::unit>{}>(std::forward(q).numerical_value_); + return make_quantity::unit>{}>( + std::forward(q).numerical_value_is_an_implementation_detail_); } #endif }; diff --git a/src/core/include/mp-units/reference.h b/src/core/include/mp-units/reference.h index 41ac4787..f33e2b38 100644 --- a/src/core/include/mp-units/reference.h +++ b/src/core/include/mp-units/reference.h @@ -203,14 +203,16 @@ template requires Quantity> [[nodiscard]] constexpr Quantity auto operator*(Q&& q, R) { - return make_quantity::reference * R{}>(std::forward(q).numerical_value_); + return make_quantity::reference * R{}>( + std::forward(q).numerical_value_is_an_implementation_detail_); } template requires Quantity> [[nodiscard]] constexpr Quantity auto operator/(Q&& q, R) { - return make_quantity::reference / R{}>(std::forward(q).numerical_value_); + return make_quantity::reference / R{}>( + std::forward(q).numerical_value_is_an_implementation_detail_); } template diff --git a/test/unit_test/runtime/linear_algebra_test.cpp b/test/unit_test/runtime/linear_algebra_test.cpp index 986204b9..492e3bf8 100644 --- a/test/unit_test/runtime/linear_algebra_test.cpp +++ b/test/unit_test/runtime/linear_algebra_test.cpp @@ -118,14 +118,14 @@ TEST_CASE("vector quantity", "[la]") SECTION("integral") { - SECTION("scalar on LHS") { CHECK((2 * v).numerical_value_ == vector{2, 4, 6}); } - SECTION("scalar on RHS") { CHECK((v * 2).numerical_value_ == vector{2, 4, 6}); } + SECTION("scalar on LHS") { CHECK((2 * v).numerical_value_in(m) == vector{2, 4, 6}); } + SECTION("scalar on RHS") { CHECK((v * 2).numerical_value_in(m) == vector{2, 4, 6}); } } SECTION("floating-point") { - SECTION("scalar on LHS") { CHECK((0.5 * v).numerical_value_ == vector{0.5, 1., 1.5}); } - SECTION("scalar on RHS") { CHECK((v * 0.5).numerical_value_ == vector{0.5, 1., 1.5}); } + SECTION("scalar on LHS") { CHECK((0.5 * v).numerical_value_in(m) == vector{0.5, 1., 1.5}); } + SECTION("scalar on RHS") { CHECK((v * 0.5).numerical_value_in(m) == vector{0.5, 1., 1.5}); } } } @@ -133,8 +133,8 @@ TEST_CASE("vector quantity", "[la]") { const auto v = vector{2, 4, 6} * isq::position_vector[m]; - SECTION("integral") { CHECK((v / 2).numerical_value_ == vector{1, 2, 3}); } - SECTION("floating-point") { CHECK((v / 0.5).numerical_value_ == vector{4., 8., 12.}); } + SECTION("integral") { CHECK((v / 2).numerical_value_in(m) == vector{1, 2, 3}); } + SECTION("floating-point") { CHECK((v / 0.5).numerical_value_in(m) == vector{4., 8., 12.}); } } SECTION("add") @@ -144,12 +144,12 @@ TEST_CASE("vector quantity", "[la]") SECTION("same unit") { const auto u = vector{3, 2, 1} * isq::position_vector[m]; - CHECK((v + u).numerical_value_ == vector{4, 4, 4}); + CHECK((v + u).numerical_value_in(m) == vector{4, 4, 4}); } SECTION("different units") { const auto u = vector{3, 2, 1} * isq::position_vector[km]; - CHECK((v + u).numerical_value_ == vector{3001, 2002, 1003}); + CHECK((v + u).numerical_value_in(m) == vector{3001, 2002, 1003}); } } @@ -160,12 +160,12 @@ TEST_CASE("vector quantity", "[la]") SECTION("same unit") { const auto u = vector{3, 2, 1} * isq::position_vector[m]; - CHECK((v - u).numerical_value_ == vector{-2, 0, 2}); + CHECK((v - u).numerical_value_in(m) == vector{-2, 0, 2}); } SECTION("different units") { const auto u = vector{3, 2, 1} * isq::position_vector[km]; - CHECK((v - u).numerical_value_ == vector{-2999, -1998, -997}); + CHECK((v - u).numerical_value_in(m) == vector{-2999, -1998, -997}); } } @@ -179,18 +179,18 @@ TEST_CASE("vector quantity", "[la]") SECTION("derived_quantity_spec") { - SECTION("scalar on LHS") { CHECK((mass * v).numerical_value_ == vector{2, 4, 6}); } - SECTION("scalar on RHS") { CHECK((v * mass).numerical_value_ == vector{2, 4, 6}); } + SECTION("scalar on LHS") { CHECK((mass * v).numerical_value_in(kg * m / s) == vector{2, 4, 6}); } + SECTION("scalar on RHS") { CHECK((v * mass).numerical_value_in(kg * m / s) == vector{2, 4, 6}); } } SECTION("quantity_cast to momentum") { SECTION("scalar on LHS") { - CHECK(quantity_cast(mass * v).numerical_value_ == vector{2, 4, 6}); + CHECK(quantity_cast(mass * v).numerical_value_in(N * s) == vector{2, 4, 6}); } SECTION("scalar on RHS") { - CHECK(quantity_cast(v * mass).numerical_value_ == vector{2, 4, 6}); + CHECK(quantity_cast(v * mass).numerical_value_in(N * s) == vector{2, 4, 6}); } } SECTION("quantity of momentum") @@ -198,12 +198,12 @@ TEST_CASE("vector quantity", "[la]") SECTION("scalar on LHS") { const quantity> momentum = mass * v; - CHECK(momentum.numerical_value_ == vector{2, 4, 6}); + CHECK(momentum.numerical_value_ref_in(N * s) == vector{2, 4, 6}); } SECTION("scalar on RHS") { const quantity> momentum = v * mass; - CHECK(momentum.numerical_value_ == vector{2, 4, 6}); + CHECK(momentum.numerical_value_ref_in(N * s) == vector{2, 4, 6}); } } } @@ -214,18 +214,18 @@ TEST_CASE("vector quantity", "[la]") SECTION("derived_quantity_spec") { - SECTION("scalar on LHS") { CHECK((mass * v).numerical_value_ == vector{0.5, 1., 1.5}); } - SECTION("scalar on RHS") { CHECK((v * mass).numerical_value_ == vector{0.5, 1., 1.5}); } + SECTION("scalar on LHS") { CHECK((mass * v).numerical_value_in(kg * m / s) == vector{0.5, 1., 1.5}); } + SECTION("scalar on RHS") { CHECK((v * mass).numerical_value_in(kg * m / s) == vector{0.5, 1., 1.5}); } } SECTION("quantity_cast to momentum") { SECTION("scalar on LHS") { - CHECK(quantity_cast(mass * v).numerical_value_ == vector{0.5, 1., 1.5}); + CHECK(quantity_cast(mass * v).numerical_value_in(N * s) == vector{0.5, 1., 1.5}); } SECTION("scalar on RHS") { - CHECK(quantity_cast(v * mass).numerical_value_ == vector{0.5, 1., 1.5}); + CHECK(quantity_cast(v * mass).numerical_value_in(N * s) == vector{0.5, 1., 1.5}); } } SECTION("quantity of momentum") @@ -233,12 +233,12 @@ TEST_CASE("vector quantity", "[la]") SECTION("scalar on LHS") { const quantity> momentum = mass * v; - CHECK(momentum.numerical_value_ == vector{0.5, 1., 1.5}); + CHECK(momentum.numerical_value_ref_in(N * s) == vector{0.5, 1., 1.5}); } SECTION("scalar on RHS") { const quantity> momentum = v * mass; - CHECK(momentum.numerical_value_ == vector{0.5, 1., 1.5}); + CHECK(momentum.numerical_value_ref_in(N * s) == vector{0.5, 1., 1.5}); } } } @@ -252,15 +252,15 @@ TEST_CASE("vector quantity", "[la]") { const auto dur = 2 * isq::duration[h]; - SECTION("derived_quantity_spec") { CHECK((pos / dur).numerical_value_ == vector{15, 10, 5}); } + SECTION("derived_quantity_spec") { CHECK((pos / dur).numerical_value_in(km / h) == vector{15, 10, 5}); } SECTION("quantity_cast to velocity") { - CHECK(quantity_cast(pos / dur).numerical_value_ == vector{15, 10, 5}); + CHECK(quantity_cast(pos / dur).numerical_value_in(km / h) == vector{15, 10, 5}); } SECTION("quantity of velocity") { const quantity> v = pos / dur; - CHECK(v.numerical_value_ == vector{15, 10, 5}); + CHECK(v.numerical_value_ref_in(km / h) == vector{15, 10, 5}); } } @@ -268,15 +268,15 @@ TEST_CASE("vector quantity", "[la]") { const auto dur = 0.5 * isq::duration[h]; - SECTION("derived_quantity_spec") { CHECK((pos / dur).numerical_value_ == vector{60, 40, 20}); } + SECTION("derived_quantity_spec") { CHECK((pos / dur).numerical_value_in(km / h) == vector{60, 40, 20}); } SECTION("quantity_cast to velocity") { - CHECK(quantity_cast(pos / dur).numerical_value_ == vector{60, 40, 20}); + CHECK(quantity_cast(pos / dur).numerical_value_in(km / h) == vector{60, 40, 20}); } SECTION("quantity of velocity") { const quantity> v = pos / dur; - CHECK(v.numerical_value_ == vector{60, 40, 20}); + CHECK(v.numerical_value_ref_in(km / h) == vector{60, 40, 20}); } } } diff --git a/test/unit_test/runtime/math_test.cpp b/test/unit_test/runtime/math_test.cpp index fdf5e1dc..e468225f 100644 --- a/test/unit_test/runtime/math_test.cpp +++ b/test/unit_test/runtime/math_test.cpp @@ -90,12 +90,12 @@ TEST_CASE("numeric_limits functions", "[limits]") { SECTION("'epsilon' works as expected using default floating type") { - REQUIRE(epsilon(isq::length[m]).numerical_value_ == + REQUIRE(epsilon(isq::length[m]).numerical_value_in(m) == std::numeric_limits::epsilon()); } SECTION("'epsilon' works as expected using integers") { - REQUIRE(epsilon(isq::length[m]).numerical_value_ == + REQUIRE(epsilon(isq::length[m]).numerical_value_in(m) == std::numeric_limits::epsilon()); } } diff --git a/test/unit_test/static/quantity_point_test.cpp b/test/unit_test/static/quantity_point_test.cpp index 0368f30b..4674bfb2 100644 --- a/test/unit_test/static/quantity_point_test.cpp +++ b/test/unit_test/static/quantity_point_test.cpp @@ -240,14 +240,14 @@ static_assert( // static member functions //////////////////////////// -static_assert(quantity_point::min().quantity_from_origin_.numerical_value_ == +static_assert(quantity_point::min().quantity_from_origin_.numerical_value_in(m) == std::numeric_limits::lowest()); -static_assert(quantity_point::max().quantity_from_origin_.numerical_value_ == +static_assert(quantity_point::max().quantity_from_origin_.numerical_value_in(m) == std::numeric_limits::max()); -static_assert(quantity_point::min().quantity_from_origin_.numerical_value_ == +static_assert(quantity_point::min().quantity_from_origin_.numerical_value_in(m) == std::numeric_limits::lowest()); -static_assert(quantity_point::max().quantity_from_origin_.numerical_value_ == +static_assert(quantity_point::max().quantity_from_origin_.numerical_value_in(m) == std::numeric_limits::max()); @@ -573,15 +573,15 @@ static_assert(is_of_type<(ground_level + isq::height(short(42) * m)).point_for(m // converting to a different unit /////////////////////////////////// -static_assert((mean_sea_level + 2. * km).in(km).quantity_from_origin_.numerical_value_ == 2.); -static_assert((mean_sea_level + 2. * km).in(m).quantity_from_origin_.numerical_value_ == 2000.); -static_assert((mean_sea_level + 2000. * m).in(km).quantity_from_origin_.numerical_value_ == 2.); -static_assert((ground_level + 2. * km).in(km).quantity_from_origin_.numerical_value_ == 2.); -static_assert((ground_level + 2. * km).in(m).quantity_from_origin_.numerical_value_ == 2000.); -static_assert((ground_level + 2000. * m).in(km).quantity_from_origin_.numerical_value_ == 2.); -static_assert((tower_peak + 2. * km).in(km).quantity_from_origin_.numerical_value_ == 2.); -static_assert((tower_peak + 2. * km).in(m).quantity_from_origin_.numerical_value_ == 2000.); -static_assert((tower_peak + 2000. * m).in(km).quantity_from_origin_.numerical_value_ == 2.); +static_assert((mean_sea_level + 2. * km).in(km).quantity_from_origin_.numerical_value_in(km) == 2.); +static_assert((mean_sea_level + 2. * km).in(m).quantity_from_origin_.numerical_value_in(m) == 2000.); +static_assert((mean_sea_level + 2000. * m).in(km).quantity_from_origin_.numerical_value_in(km) == 2.); +static_assert((ground_level + 2. * km).in(km).quantity_from_origin_.numerical_value_in(km) == 2.); +static_assert((ground_level + 2. * km).in(m).quantity_from_origin_.numerical_value_in(m) == 2000.); +static_assert((ground_level + 2000. * m).in(km).quantity_from_origin_.numerical_value_in(km) == 2.); +static_assert((tower_peak + 2. * km).in(km).quantity_from_origin_.numerical_value_in(km) == 2.); +static_assert((tower_peak + 2. * km).in(m).quantity_from_origin_.numerical_value_in(m) == 2000.); +static_assert((tower_peak + 2000. * m).in(km).quantity_from_origin_.numerical_value_in(km) == 2.); template typename QP> concept invalid_unit_conversion = requires { @@ -652,14 +652,14 @@ static_assert([](auto v) { //////////////////////// // same type -static_assert((mean_sea_level + 1 * m += 1 * m).quantity_from_origin_.numerical_value_ == 2); -static_assert((mean_sea_level + 2 * m -= 1 * m).quantity_from_origin_.numerical_value_ == 1); +static_assert((mean_sea_level + 1 * m += 1 * m).quantity_from_origin_.numerical_value_in(m) == 2); +static_assert((mean_sea_level + 2 * m -= 1 * m).quantity_from_origin_.numerical_value_in(m) == 1); // different types -static_assert((mean_sea_level + 2.5 * m += 3 * m).quantity_from_origin_.numerical_value_ == 5.5); -static_assert((mean_sea_level + 123 * m += 1 * km).quantity_from_origin_.numerical_value_ == 1123); -static_assert((mean_sea_level + 5.5 * m -= 3 * m).quantity_from_origin_.numerical_value_ == 2.5); -static_assert((mean_sea_level + 1123 * m -= 1 * km).quantity_from_origin_.numerical_value_ == 123); +static_assert((mean_sea_level + 2.5 * m += 3 * m).quantity_from_origin_.numerical_value_in(m) == 5.5); +static_assert((mean_sea_level + 123 * m += 1 * km).quantity_from_origin_.numerical_value_in(m) == 1123); +static_assert((mean_sea_level + 5.5 * m -= 3 * m).quantity_from_origin_.numerical_value_in(m) == 2.5); +static_assert((mean_sea_level + 1123 * m -= 1 * km).quantity_from_origin_.numerical_value_in(m) == 123); template typename QP> @@ -931,24 +931,24 @@ static_assert(is_of_type<(1 * m + tower_peak) - (1 * m + other_ground_level), qu // check for integral types promotion static_assert(is_same_v); static_assert(is_same_v); static_assert(is_same_v); +static_assert(is_same_v); -static_assert( - is_same_v< - decltype(((mean_sea_level + std::uint8_t(0) * m) - (mean_sea_level + std::uint8_t(0) * m)).numerical_value_), int>); static_assert(((mean_sea_level + std::uint8_t(128) * m) + std::uint8_t(128) * m) - .quantity_from_origin_.numerical_value_ == std::uint8_t(128) + std::uint8_t(128)); + .quantity_from_origin_.numerical_value_in(m) == std::uint8_t(128) + std::uint8_t(128)); static_assert((std::uint8_t(128) * m + (mean_sea_level + std::uint8_t(128) * m)) - .quantity_from_origin_.numerical_value_ == std::uint8_t(128) + std::uint8_t(128)); -static_assert(((mean_sea_level + std::uint8_t(0) * m) - std::uint8_t(1) * m).quantity_from_origin_.numerical_value_ == - std::uint8_t(0) - std::uint8_t(1)); -static_assert(((mean_sea_level + std::uint8_t(0) * m) - (mean_sea_level + std::uint8_t(1) * m)).numerical_value_ == + .quantity_from_origin_.numerical_value_in(m) == std::uint8_t(128) + std::uint8_t(128)); +static_assert(((mean_sea_level + std::uint8_t(0) * m) - std::uint8_t(1) * m) + .quantity_from_origin_.numerical_value_in(m) == std::uint8_t(0) - std::uint8_t(1)); +static_assert(((mean_sea_level + std::uint8_t(0) * m) - (mean_sea_level + std::uint8_t(1) * m)).numerical_value_in(m) == std::uint8_t(0) - std::uint8_t(1)); // different representation types @@ -1003,39 +1003,39 @@ static_assert(is_of_type<(mean_sea_level + 1 * km) - (mean_sea_level + 1. * m), static_assert(is_of_type<(mean_sea_level + 1. * km) - (mean_sea_level + 1. * m), quantity>); -static_assert(((mean_sea_level + 1 * m) + 1 * m).quantity_from_origin_.numerical_value_ == 2); -static_assert((1 * m + (mean_sea_level + 1 * m)).quantity_from_origin_.numerical_value_ == 2); -static_assert(((mean_sea_level + 1 * m) + 1 * km).quantity_from_origin_.numerical_value_ == 1001); -static_assert((1 * m + (mean_sea_level + 1 * km)).quantity_from_origin_.numerical_value_ == 1001); -static_assert(((mean_sea_level + 1 * km) + 1 * m).quantity_from_origin_.numerical_value_ == 1001); -static_assert((1 * km + (mean_sea_level + 1 * m)).quantity_from_origin_.numerical_value_ == 1001); -static_assert(((mean_sea_level + 2 * m) - 1 * m).quantity_from_origin_.numerical_value_ == 1); -static_assert(((mean_sea_level + 1 * km) - 1 * m).quantity_from_origin_.numerical_value_ == 999); +static_assert(((mean_sea_level + 1 * m) + 1 * m).quantity_from_origin_.numerical_value_in(m) == 2); +static_assert((1 * m + (mean_sea_level + 1 * m)).quantity_from_origin_.numerical_value_in(m) == 2); +static_assert(((mean_sea_level + 1 * m) + 1 * km).quantity_from_origin_.numerical_value_in(m) == 1001); +static_assert((1 * m + (mean_sea_level + 1 * km)).quantity_from_origin_.numerical_value_in(m) == 1001); +static_assert(((mean_sea_level + 1 * km) + 1 * m).quantity_from_origin_.numerical_value_in(m) == 1001); +static_assert((1 * km + (mean_sea_level + 1 * m)).quantity_from_origin_.numerical_value_in(m) == 1001); +static_assert(((mean_sea_level + 2 * m) - 1 * m).quantity_from_origin_.numerical_value_in(m) == 1); +static_assert(((mean_sea_level + 1 * km) - 1 * m).quantity_from_origin_.numerical_value_in(m) == 999); -static_assert(((mean_sea_level + 1.5 * m) + 1 * m).quantity_from_origin_.numerical_value_ == 2.5); -static_assert((1.5 * m + (mean_sea_level + 1 * m)).quantity_from_origin_.numerical_value_ == 2.5); -static_assert(((mean_sea_level + 1.5 * m) + 1 * km).quantity_from_origin_.numerical_value_ == 1001.5); -static_assert((1.5 * m + (mean_sea_level + 1 * km)).quantity_from_origin_.numerical_value_ == 1001.5); -static_assert(((mean_sea_level + 1.5 * km) + 1 * m).quantity_from_origin_.numerical_value_ == 1501); -static_assert((1.5 * km + (mean_sea_level + 1 * m)).quantity_from_origin_.numerical_value_ == 1501); -static_assert(((mean_sea_level + 2.5 * m) - 1 * m).quantity_from_origin_.numerical_value_ == 1.5); -static_assert(((mean_sea_level + 1.5 * km) - 1 * m).quantity_from_origin_.numerical_value_ == 1499); +static_assert(((mean_sea_level + 1.5 * m) + 1 * m).quantity_from_origin_.numerical_value_in(m) == 2.5); +static_assert((1.5 * m + (mean_sea_level + 1 * m)).quantity_from_origin_.numerical_value_in(m) == 2.5); +static_assert(((mean_sea_level + 1.5 * m) + 1 * km).quantity_from_origin_.numerical_value_in(m) == 1001.5); +static_assert((1.5 * m + (mean_sea_level + 1 * km)).quantity_from_origin_.numerical_value_in(m) == 1001.5); +static_assert(((mean_sea_level + 1.5 * km) + 1 * m).quantity_from_origin_.numerical_value_in(m) == 1501); +static_assert((1.5 * km + (mean_sea_level + 1 * m)).quantity_from_origin_.numerical_value_in(m) == 1501); +static_assert(((mean_sea_level + 2.5 * m) - 1 * m).quantity_from_origin_.numerical_value_in(m) == 1.5); +static_assert(((mean_sea_level + 1.5 * km) - 1 * m).quantity_from_origin_.numerical_value_in(m) == 1499); -static_assert(((mean_sea_level + 1 * m) + 1.5 * m).quantity_from_origin_.numerical_value_ == 2.5); -static_assert((1 * m + (mean_sea_level + 1.5 * m)).quantity_from_origin_.numerical_value_ == 2.5); -static_assert(((mean_sea_level + 1 * m) + 1.5 * km).quantity_from_origin_.numerical_value_ == 1501); -static_assert((1 * m + (mean_sea_level + 1.5 * km)).quantity_from_origin_.numerical_value_ == 1501); -static_assert(((mean_sea_level + 1 * km) + 1.5 * m).quantity_from_origin_.numerical_value_ == 1001.5); -static_assert((1 * km + (mean_sea_level + 1.5 * m)).quantity_from_origin_.numerical_value_ == 1001.5); -static_assert(((mean_sea_level + 2 * m) - 1.5 * m).quantity_from_origin_.numerical_value_ == 0.5); -static_assert(((mean_sea_level + 1 * km) - 1.5 * m).quantity_from_origin_.numerical_value_ == 998.5); +static_assert(((mean_sea_level + 1 * m) + 1.5 * m).quantity_from_origin_.numerical_value_in(m) == 2.5); +static_assert((1 * m + (mean_sea_level + 1.5 * m)).quantity_from_origin_.numerical_value_in(m) == 2.5); +static_assert(((mean_sea_level + 1 * m) + 1.5 * km).quantity_from_origin_.numerical_value_in(m) == 1501); +static_assert((1 * m + (mean_sea_level + 1.5 * km)).quantity_from_origin_.numerical_value_in(m) == 1501); +static_assert(((mean_sea_level + 1 * km) + 1.5 * m).quantity_from_origin_.numerical_value_in(m) == 1001.5); +static_assert((1 * km + (mean_sea_level + 1.5 * m)).quantity_from_origin_.numerical_value_in(m) == 1001.5); +static_assert(((mean_sea_level + 2 * m) - 1.5 * m).quantity_from_origin_.numerical_value_in(m) == 0.5); +static_assert(((mean_sea_level + 1 * km) - 1.5 * m).quantity_from_origin_.numerical_value_in(m) == 998.5); -static_assert(((mean_sea_level + 2 * m) - (mean_sea_level + 1 * m)).numerical_value_ == 1); -static_assert(((mean_sea_level + 1 * km) - (mean_sea_level + 1 * m)).numerical_value_ == 999); -static_assert(((mean_sea_level + 2.5 * m) - (mean_sea_level + 1 * m)).numerical_value_ == 1.5); -static_assert(((mean_sea_level + 1.5 * km) - (mean_sea_level + 1 * m)).numerical_value_ == 1499); -static_assert(((mean_sea_level + 2 * m) - (mean_sea_level + 1.5 * m)).numerical_value_ == 0.5); -static_assert(((mean_sea_level + 1 * km) - (mean_sea_level + 1.5 * m)).numerical_value_ == 998.5); +static_assert(((mean_sea_level + 2 * m) - (mean_sea_level + 1 * m)).numerical_value_in(m) == 1); +static_assert(((mean_sea_level + 1 * km) - (mean_sea_level + 1 * m)).numerical_value_in(m) == 999); +static_assert(((mean_sea_level + 2.5 * m) - (mean_sea_level + 1 * m)).numerical_value_in(m) == 1.5); +static_assert(((mean_sea_level + 1.5 * km) - (mean_sea_level + 1 * m)).numerical_value_in(m) == 1499); +static_assert(((mean_sea_level + 2 * m) - (mean_sea_level + 1.5 * m)).numerical_value_in(m) == 0.5); +static_assert(((mean_sea_level + 1 * km) - (mean_sea_level + 1.5 * m)).numerical_value_in(m) == 998.5); static_assert((mean_sea_level + 42 * m) - (ground_level + 42 * m) == -42 * m); static_assert((ground_level + 42 * m) - (mean_sea_level + 42 * m) == 42 * m); diff --git a/test/unit_test/static/quantity_test.cpp b/test/unit_test/static/quantity_test.cpp index 60c90c9e..47ed833c 100644 --- a/test/unit_test/static/quantity_test.cpp +++ b/test/unit_test/static/quantity_test.cpp @@ -108,14 +108,14 @@ static_assert(is_same_v::rep, int>); // static member functions //////////////////////////// -static_assert(quantity::zero().numerical_value_ == 0); -static_assert(quantity::one().numerical_value_ == 1); -static_assert(quantity::min().numerical_value_ == std::numeric_limits::lowest()); -static_assert(quantity::max().numerical_value_ == std::numeric_limits::max()); -static_assert(quantity::zero().numerical_value_ == 0.0); -static_assert(quantity::one().numerical_value_ == 1.0); -static_assert(quantity::min().numerical_value_ == std::numeric_limits::lowest()); -static_assert(quantity::max().numerical_value_ == std::numeric_limits::max()); +static_assert(quantity::zero().numerical_value_in(m) == 0); +static_assert(quantity::one().numerical_value_in(m) == 1); +static_assert(quantity::min().numerical_value_in(m) == std::numeric_limits::lowest()); +static_assert(quantity::max().numerical_value_in(m) == std::numeric_limits::max()); +static_assert(quantity::zero().numerical_value_in(m) == 0.0); +static_assert(quantity::one().numerical_value_in(m) == 1.0); +static_assert(quantity::min().numerical_value_in(m) == std::numeric_limits::lowest()); +static_assert(quantity::max().numerical_value_in(m) == std::numeric_limits::max()); ////////////////////////////// @@ -186,10 +186,10 @@ static_assert(std::convertible_to, quantity(123 * m).numerical_value_ == 123); -static_assert(quantity(2 * km).numerical_value_ == 2000); -static_assert(quantity(2 * km).numerical_value_ == 2); -static_assert(quantity(1500 * m).numerical_value_ == 1.5); +static_assert(quantity(123 * m).numerical_value_in(m) == 123); +static_assert(quantity(2 * km).numerical_value_in(m) == 2000); +static_assert(quantity(2 * km).numerical_value_in(km) == 2); +static_assert(quantity(1500 * m).numerical_value_in(km) == 1.5); /////////////////////////////////// @@ -200,22 +200,22 @@ static_assert(is_of_type<(2. * km).in(m), quantity>); static_assert(is_of_type>); static_assert(is_of_type>); -static_assert(quantity(2. * km).in(km).numerical_value_ == 2.); -static_assert(quantity(2. * km).in(m).numerical_value_ == 2000.); -static_assert(quantity(2000. * m).in(km).numerical_value_ == 2.); -static_assert(quantity(2 * km).in(km).numerical_value_ == 2); -static_assert(quantity(2 * km).in(m).numerical_value_ == 2000); +static_assert(quantity(2. * km).in(km).numerical_value_in(km) == 2.); +static_assert(quantity(2. * km).in(m).numerical_value_in(m) == 2000.); +static_assert(quantity(2000. * m).in(km).numerical_value_in(km) == 2.); +static_assert(quantity(2 * km).in(km).numerical_value_in(km) == 2); +static_assert(quantity(2 * km).in(m).numerical_value_in(m) == 2000); static_assert(is_of_type<(2. * km).force_in(m), quantity>); static_assert(is_of_type>); static_assert(is_of_type>); -static_assert(quantity(2. * km).force_in(km).numerical_value_ == 2.); -static_assert(quantity(2. * km).force_in(m).numerical_value_ == 2000.); -static_assert(quantity(2000. * m).force_in(km).numerical_value_ == 2.); -static_assert(quantity(2 * km).force_in(km).numerical_value_ == 2); -static_assert(quantity(2 * km).force_in(m).numerical_value_ == 2000); -static_assert(quantity(2000 * m).force_in(km).numerical_value_ == 2); +static_assert(quantity(2. * km).force_in(km).numerical_value_in(km) == 2.); +static_assert(quantity(2. * km).force_in(m).numerical_value_in(m) == 2000.); +static_assert(quantity(2000. * m).force_in(km).numerical_value_in(km) == 2.); +static_assert(quantity(2 * km).force_in(km).numerical_value_in(km) == 2); +static_assert(quantity(2 * km).force_in(m).numerical_value_in(m) == 2000); +static_assert(quantity(2000 * m).force_in(km).numerical_value_in(km) == 2); template typename Q> concept invalid_unit_conversion = requires { @@ -317,28 +317,28 @@ static_assert([] { auto l1(1 * m), l2(2 * m); return l2 = l1; }() - .numerical_value_ == 1); + .numerical_value_in(m) == 1); static_assert([] { const auto l1(1 * m); auto l2(2 * m); return l2 = l1; }() - .numerical_value_ == 1); + .numerical_value_in(m) == 1); static_assert([]() { auto l1(1 * m), l2(2 * m); return l2 = std::move(l1); }() - .numerical_value_ == 1); + .numerical_value_in(m) == 1); //////////////////// // unary operators //////////////////// -static_assert((+123 * m).numerical_value_ == 123); -static_assert((-123 * m).numerical_value_ == -123); -static_assert((+(-123 * m)).numerical_value_ == -123); -static_assert((-(-123 * m)).numerical_value_ == 123); +static_assert((+123 * m).numerical_value_in(m) == 123); +static_assert((-123 * m).numerical_value_in(m) == -123); +static_assert((+(-123 * m)).numerical_value_in(m) == -123); +static_assert((-(-123 * m)).numerical_value_in(m) == 123); static_assert([](auto v) { auto vv = v++; @@ -357,7 +357,7 @@ static_assert([](auto v) { return std::pair(v, vv); }(123 * m) == std::pair(122 * m, 122 * m)); -static_assert(is_same_v); +static_assert(is_same_v); //////////////////////// @@ -365,31 +365,31 @@ static_assert(is_same_v); //////////////////////// // same type -static_assert((1 * m += 1 * m).numerical_value_ == 2); -static_assert((2 * m -= 1 * m).numerical_value_ == 1); -static_assert((1 * m *= 2).numerical_value_ == 2); -static_assert((2 * m /= 2).numerical_value_ == 1); -static_assert((1 * m *= 2 * one).numerical_value_ == 2); -static_assert((2 * m /= 2 * one).numerical_value_ == 1); -static_assert((7 * m %= 2 * m).numerical_value_ == 1); +static_assert((1 * m += 1 * m).numerical_value_in(m) == 2); +static_assert((2 * m -= 1 * m).numerical_value_in(m) == 1); +static_assert((1 * m *= 2).numerical_value_in(m) == 2); +static_assert((2 * m /= 2).numerical_value_in(m) == 1); +static_assert((1 * m *= 2 * one).numerical_value_in(m) == 2); +static_assert((2 * m /= 2 * one).numerical_value_in(m) == 1); +static_assert((7 * m %= 2 * m).numerical_value_in(m) == 1); // different types -static_assert((2.5 * m += 3 * m).numerical_value_ == 5.5); -static_assert((123 * m += 1 * km).numerical_value_ == 1123); -static_assert((5.5 * m -= 3 * m).numerical_value_ == 2.5); -static_assert((1123 * m -= 1 * km).numerical_value_ == 123); -static_assert((2.5 * m *= 3).numerical_value_ == 7.5); -static_assert((7.5 * m /= 3).numerical_value_ == 2.5); -static_assert((2.5 * m *= 3 * one).numerical_value_ == 7.5); -static_assert((7.5 * m /= 3 * one).numerical_value_ == 2.5); -static_assert((3500 * m %= 1 * km).numerical_value_ == 500); +static_assert((2.5 * m += 3 * m).numerical_value_in(m) == 5.5); +static_assert((123 * m += 1 * km).numerical_value_in(m) == 1123); +static_assert((5.5 * m -= 3 * m).numerical_value_in(m) == 2.5); +static_assert((1123 * m -= 1 * km).numerical_value_in(m) == 123); +static_assert((2.5 * m *= 3).numerical_value_in(m) == 7.5); +static_assert((7.5 * m /= 3).numerical_value_in(m) == 2.5); +static_assert((2.5 * m *= 3 * one).numerical_value_in(m) == 7.5); +static_assert((7.5 * m /= 3 * one).numerical_value_in(m) == 2.5); +static_assert((3500 * m %= 1 * km).numerical_value_in(m) == 500); -// static_assert((std::uint8_t(255) * m %= 256 * m).numerical_value_ == [] { +// static_assert((std::uint8_t(255) * m %= 256 * m).numerical_value_in(m) == [] { // std::uint8_t ui(255); // return ui %= 256; // }()); // UB // TODO: Fix -static_assert((std::uint8_t(255) * m %= 257 * m).numerical_value_ != [] { +static_assert((std::uint8_t(255) * m %= 257 * m).numerical_value_in(m) != [] { std::uint8_t ui(255); return ui %= 257; }()); @@ -399,10 +399,10 @@ static_assert((std::uint8_t(255) * m %= 257 * m).numerical_value_ != [] { #ifndef MP_UNITS_COMP_MSVC // next two lines trigger conversions warnings // (warning disabled in CMake for this file) -static_assert((22 * m *= 33.33).numerical_value_ == 733); -static_assert((22 * m /= 3.33).numerical_value_ == 6); -static_assert((22 * m *= 33.33 * one).numerical_value_ == 733); -static_assert((22 * m /= 3.33 * one).numerical_value_ == 6); +static_assert((22 * m *= 33.33).numerical_value_in(m) == 733); +static_assert((22 * m /= 3.33).numerical_value_in(m) == 6); +static_assert((22 * m *= 33.33 * one).numerical_value_in(m) == 733); +static_assert((22 * m /= 3.33 * one).numerical_value_in(m) == 6); #endif template typename Q> @@ -530,9 +530,9 @@ static_assert(is_of_type<4 * one % (2 * one), quantity>); // check for integral types promotion static_assert(is_same_v); static_assert(is_same_v); -static_assert((std::uint8_t(128) * m + std::uint8_t(128) * m).numerical_value_ == +static_assert((std::uint8_t(128) * m + std::uint8_t(128) * m).numerical_value_in(m) == std::uint8_t(128) + std::uint8_t(128)); -static_assert((std::uint8_t(0) * m - std::uint8_t(1) * m).numerical_value_ == std::uint8_t(0) - std::uint8_t(1)); +static_assert((std::uint8_t(0) * m - std::uint8_t(1) * m).numerical_value_in(m) == std::uint8_t(0) - std::uint8_t(1)); static_assert( is_same_v); @@ -612,67 +612,67 @@ static_assert(is_of_type<1 * m / (1 * s), quantity>{}, int>>); static_assert(is_of_type<1 * min / (1 * m), quantity>{}, int>>); -static_assert((1 * m + 1 * m).numerical_value_ == 2); -static_assert((1 * m + 1 * km).numerical_value_ == 1001); -static_assert((1 * km + 1 * m).numerical_value_ == 1001); -static_assert((2 * m - 1 * m).numerical_value_ == 1); -static_assert((1 * km - 1 * m).numerical_value_ == 999); -static_assert((2 * m * 2).numerical_value_ == 4); -static_assert((2 * m * (2 * one)).numerical_value_ == 4); -static_assert((2 * m * (2 * percent)).numerical_value_ == 4); -static_assert((3 * 3 * m).numerical_value_ == 9); -static_assert(((3 * one) * (3 * m)).numerical_value_ == 9); -static_assert(((3 * percent) * (3 * m)).numerical_value_ == 9); -static_assert((4 * m / 2).numerical_value_ == 2); -static_assert((4 * m / (2 * one)).numerical_value_ == 2); -static_assert((4 * m / (2 * percent)).numerical_value_ == 2); -static_assert((4 * km / (2 * m)).numerical_value_ == 2); -static_assert((4000 * m / (2 * m)).numerical_value_ == 2000); +static_assert((1 * m + 1 * m).numerical_value_in(m) == 2); +static_assert((1 * m + 1 * km).numerical_value_in(m) == 1001); +static_assert((1 * km + 1 * m).numerical_value_in(m) == 1001); +static_assert((2 * m - 1 * m).numerical_value_in(m) == 1); +static_assert((1 * km - 1 * m).numerical_value_in(m) == 999); +static_assert((2 * m * 2).numerical_value_in(m) == 4); +static_assert((2 * m * (2 * one)).numerical_value_in(m) == 4); +static_assert((2 * m * (2 * percent)).numerical_value_in(percent * m) == 4); +static_assert((3 * 3 * m).numerical_value_in(m) == 9); +static_assert(((3 * one) * (3 * m)).numerical_value_in(m) == 9); +static_assert(((3 * percent) * (3 * m)).numerical_value_in(percent * m) == 9); +static_assert((4 * m / 2).numerical_value_in(m) == 2); +static_assert((4 * m / (2 * one)).numerical_value_in(m) == 2); +static_assert((4 * m / (2 * percent)).numerical_value_in(m / percent) == 2); +static_assert((4 * km / (2 * m)).numerical_value_in(km / m) == 2); +static_assert((4000 * m / (2 * m)).numerical_value_in(one) == 2000); -static_assert((1.5 * m + 1 * m).numerical_value_ == 2.5); -static_assert((1.5 * m + 1 * km).numerical_value_ == 1001.5); -static_assert((1.5 * km + 1 * m).numerical_value_ == 1501); -static_assert((2.5 * m - 1 * m).numerical_value_ == 1.5); -static_assert((1.5 * km - 1 * m).numerical_value_ == 1499); -static_assert((2.5 * m * 2).numerical_value_ == 5); -static_assert((2.5 * m * (2 * one)).numerical_value_ == 5); -static_assert((2.5 * m * (2 * percent)).numerical_value_ == 5); -static_assert((2.5L * (2 * m)).numerical_value_ == 5); -static_assert((2.5L * one * (2 * m)).numerical_value_ == 5); -static_assert((2.5L * percent * (2 * m)).numerical_value_ == 5); -static_assert((5. * m / 2).numerical_value_ == 2.5); -static_assert((5. * m / (2 * one)).numerical_value_ == 2.5); -static_assert((5. * m / (2 * percent)).numerical_value_ == 2.5); -static_assert((5. * km / (2 * m)).numerical_value_ == 2.5); -static_assert((5000. * m / (2 * m)).numerical_value_ == 2500); +static_assert((1.5 * m + 1 * m).numerical_value_in(m) == 2.5); +static_assert((1.5 * m + 1 * km).numerical_value_in(m) == 1001.5); +static_assert((1.5 * km + 1 * m).numerical_value_in(m) == 1501); +static_assert((2.5 * m - 1 * m).numerical_value_in(m) == 1.5); +static_assert((1.5 * km - 1 * m).numerical_value_in(m) == 1499); +static_assert((2.5 * m * 2).numerical_value_in(m) == 5); +static_assert((2.5 * m * (2 * one)).numerical_value_in(m) == 5); +static_assert((2.5 * m * (2 * percent)).numerical_value_in(m * percent) == 5); +static_assert((2.5L * (2 * m)).numerical_value_in(m) == 5); +static_assert((2.5L * one * (2 * m)).numerical_value_in(m) == 5); +static_assert((2.5L * percent * (2 * m)).numerical_value_in(m * percent) == 5); +static_assert((5. * m / 2).numerical_value_in(m) == 2.5); +static_assert((5. * m / (2 * one)).numerical_value_in(m) == 2.5); +static_assert((5. * m / (2 * percent)).numerical_value_in(m / percent) == 2.5); +static_assert((5. * km / (2 * m)).numerical_value_in(km / m) == 2.5); +static_assert((5000. * m / (2 * m)).numerical_value_in(one) == 2500); -static_assert((1 * m + 1.5 * m).numerical_value_ == 2.5); -static_assert((1 * m + 1.5 * km).numerical_value_ == 1501); -static_assert((1 * km + 1.5 * m).numerical_value_ == 1001.5); -static_assert((2 * m - 1.5 * m).numerical_value_ == 0.5); -static_assert((1 * km - 1.5 * m).numerical_value_ == 998.5); -static_assert((2 * m * 2.5L).numerical_value_ == 5); -static_assert((2 * m * (2.5L * one)).numerical_value_ == 5); -static_assert((2 * m * (2.5L * percent)).numerical_value_ == 5); -static_assert((2 * 2.5 * m).numerical_value_ == 5); -static_assert((2 * one * (2.5 * m)).numerical_value_ == 5); -static_assert((2 * percent * (2.5 * m)).numerical_value_ == 5); -static_assert((5 * m / 2.5L).numerical_value_ == 2); -static_assert((5 * m / (2.5L * one)).numerical_value_ == 2); -static_assert((5 * m / (2.5L * percent)).numerical_value_ == 2); -static_assert((5 * km / (2.5 * m)).numerical_value_ == 2); -static_assert((5000 * m / (2.5 * m)).numerical_value_ == 2000); +static_assert((1 * m + 1.5 * m).numerical_value_in(m) == 2.5); +static_assert((1 * m + 1.5 * km).numerical_value_in(m) == 1501); +static_assert((1 * km + 1.5 * m).numerical_value_in(m) == 1001.5); +static_assert((2 * m - 1.5 * m).numerical_value_in(m) == 0.5); +static_assert((1 * km - 1.5 * m).numerical_value_in(m) == 998.5); +static_assert((2 * m * 2.5L).numerical_value_in(m) == 5); +static_assert((2 * m * (2.5L * one)).numerical_value_in(m) == 5); +static_assert((2 * m * (2.5L * percent)).numerical_value_in(m * percent) == 5); +static_assert((2 * 2.5 * m).numerical_value_in(m) == 5); +static_assert((2 * one * (2.5 * m)).numerical_value_in(m) == 5); +static_assert((2 * percent * (2.5 * m)).numerical_value_in(m * percent) == 5); +static_assert((5 * m / 2.5L).numerical_value_in(m) == 2); +static_assert((5 * m / (2.5L * one)).numerical_value_in(m) == 2); +static_assert((5 * m / (2.5L * percent)).numerical_value_in(m / percent) == 2); +static_assert((5 * km / (2.5 * m)).numerical_value_in(km / m) == 2); +static_assert((5000 * m / (2.5 * m)).numerical_value_in(one) == 2000); -static_assert((7 * m % (2 * m)).numerical_value_ == 1); -static_assert((7 * km % (2000 * m)).numerical_value_ == 1000); -static_assert((1300 * m % (1 * km)).numerical_value_ == 300); -static_assert((7 * one % (2 * one)).numerical_value_ == 1); +static_assert((7 * m % (2 * m)).numerical_value_in(m) == 1); +static_assert((7 * km % (2000 * m)).numerical_value_in(m) == 1000); +static_assert((1300 * m % (1 * km)).numerical_value_in(m) == 300); +static_assert((7 * one % (2 * one)).numerical_value_in(one) == 1); static_assert((10 * m2 * (10 * m2)) / (50 * m2) == 2 * m2); -static_assert((10 * km / (5 * m)).numerical_value_ == 2); +static_assert((10 * km / (5 * m)).numerical_value_in(km / m) == 2); static_assert((10 * km / (5 * m)).numerical_value_in(one) == 2000); -static_assert((10 * s * (2 * kHz)).numerical_value_ == 20); +static_assert((10 * s * (2 * kHz)).numerical_value_in(s * kHz) == 20); // commutativity and associativity static_assert(10 * isq::length[si::metre] / (2 * isq::time[s]) + 5 * isq::speed[m / s] == 10 * isq::speed[m / s]); @@ -758,9 +758,10 @@ static_assert(1 * one + 30 * percent == (100 + 30) * percent); static_assert(is_same_v); static_assert(is_same_v); -static_assert((std::uint8_t(128) * one + std::uint8_t(128) * one).numerical_value_ == +static_assert((std::uint8_t(128) * one + std::uint8_t(128) * one).numerical_value_in(one) == std::uint8_t(128) + std::uint8_t(128)); -static_assert((std::uint8_t(0) * one - std::uint8_t(1) * one).numerical_value_ == std::uint8_t(0) - std::uint8_t(1)); +static_assert((std::uint8_t(0) * one - std::uint8_t(1) * one).numerical_value_in(one) == + std::uint8_t(0) - std::uint8_t(1)); static_assert(is_same_v); @@ -905,14 +906,14 @@ static_assert((50. * percent).numerical_value_in(one) == 0.5); // value_cast ////////////////// -static_assert(value_cast(2 * km).numerical_value_ == 2000); -static_assert(value_cast(2000 * m).numerical_value_ == 2); -static_assert(value_cast(1.23 * m).numerical_value_ == 1); -static_assert(value_cast(2000.0 * m / (3600.0 * s)).numerical_value_ == 2); +static_assert(value_cast(2 * km).numerical_value_in(m) == 2000); +static_assert(value_cast(2000 * m).numerical_value_in(km) == 2); +static_assert(value_cast(1.23 * m).numerical_value_in(m) == 1); +static_assert(value_cast(2000.0 * m / (3600.0 * s)).numerical_value_in(km / h) == 2); -static_assert((2 * km).force_in(m).numerical_value_ == 2000); -static_assert((2000 * m).force_in(km).numerical_value_ == 2); -static_assert((2000.0 * m / (3600.0 * s)).force_in(km / h).numerical_value_ == 2); +static_assert((2 * km).force_in(m).numerical_value_in(m) == 2000); +static_assert((2000 * m).force_in(km).numerical_value_in(km) == 2); +static_assert((2000.0 * m / (3600.0 * s)).force_in(km / h).numerical_value_in(km / h) == 2); ////////////////// // quantity_cast