diff --git a/src/include/units/ratio.h b/src/include/units/ratio.h index 7d20362f..a47020ae 100644 --- a/src/include/units/ratio.h +++ b/src/include/units/ratio.h @@ -200,10 +200,23 @@ constexpr std::intmax_t sqrt_impl(std::intmax_t v, std::intmax_t l, std::intmax_ static constexpr std::intmax_t sqrt_impl(std::intmax_t v) { return sqrt_impl(v, 1, v); } +template +constexpr std::tuple make_exp_even() +{ + if constexpr (R::exp % 2 == 0) + return {R::num, R::den, R::exp}; // already even (incl zero) + + // safely make exp even, so it can be divided by 2 for square root + if constexpr (R::exp > 0) + return {R::num * 10, R::den, R::exp - 1}; + else + return {R::num, R::den * 10, R::exp + 1}; +} + template struct ratio_sqrt_impl { - // TODO(#58) Provide sqrt on exp - using type = ratio; + constexpr static auto even = detail::make_exp_even(); + using type = ratio(even)), detail::sqrt_impl(std::get<1>(even)), std::get<2>(even) / 2>; }; template diff --git a/test/unit_test/static/math_test.cpp b/test/unit_test/static/math_test.cpp index 178ff226..766ac726 100644 --- a/test/unit_test/static/math_test.cpp +++ b/test/unit_test/static/math_test.cpp @@ -36,7 +36,7 @@ namespace { static_assert(std::is_same_v(2km)), decltype(4km2)>); static_assert(std::is_same_v(2ft)), decltype(4ft2)>); static_assert(std::is_same_v); - // static_assert(std::is_same_v); - // static_assert(std::is_same_v); + static_assert(std::is_same_v); + static_assert(std::is_same_v); } // namespace