From 36b1707da0f71b08a7a992bfb6a0fccf1b7a356d Mon Sep 17 00:00:00 2001 From: Mateusz Pusz Date: Sun, 24 Nov 2024 13:58:04 +0100 Subject: [PATCH] perf: `get_complexity`, `explode`, and `extract_convertible_quantities` results caching added --- .../mp-units/framework/quantity_spec.h | 58 ++++++++++++++----- 1 file changed, 44 insertions(+), 14 deletions(-) diff --git a/src/core/include/mp-units/framework/quantity_spec.h b/src/core/include/mp-units/framework/quantity_spec.h index 6226cdde1..c0395069d 100644 --- a/src/core/include/mp-units/framework/quantity_spec.h +++ b/src/core/include/mp-units/framework/quantity_spec.h @@ -622,7 +622,7 @@ template } template -[[nodiscard]] consteval int get_complexity(Q) +[[nodiscard]] consteval int get_complexity_impl(Q) { if constexpr (DerivedQuantitySpec) return max(get_complexity(typename Q::_num_{}), get_complexity(typename Q::_den_{})); @@ -632,6 +632,15 @@ template return 0; } +template +constexpr auto get_complexity_result = get_complexity_impl(Q{}); + +template +[[nodiscard]] consteval int get_complexity(Q) +{ + return get_complexity_result; +} + // dimension_one is always the last one // otherwise, sort by typename template @@ -719,14 +728,17 @@ explode_result(Q) -> explode_result; #endif -template +template [[nodiscard]] consteval auto explode(Q q); +template +[[nodiscard]] consteval auto explode_impl(Q q); + template -[[nodiscard]] consteval auto explode(Q q); +[[nodiscard]] consteval auto explode_impl(Q q); template -[[nodiscard]] consteval auto explode(Q, type_list, type_list) +[[nodiscard]] consteval auto explode_impl(Q, type_list, type_list) { constexpr auto num = get_complexity(Num{}); constexpr auto den = get_complexity(Den{}); @@ -751,7 +763,7 @@ template -[[nodiscard]] consteval auto explode(Q, type_list, type_list<>) +[[nodiscard]] consteval auto explode_impl(Q, type_list, type_list<>) { constexpr auto n = get_complexity(Num{}); if constexpr (n == Complexity || !requires { explode_to_equation(Num{}); }) @@ -763,7 +775,7 @@ template } template -[[nodiscard]] consteval auto explode(Q, type_list<>, type_list) +[[nodiscard]] consteval auto explode_impl(Q, type_list<>, type_list) { constexpr auto den = get_complexity(Den{}); if constexpr (den == Complexity || !requires { explode_to_equation(Den{}); }) @@ -776,24 +788,24 @@ template } template -[[nodiscard]] consteval auto explode(Q, type_list<>, type_list<>) +[[nodiscard]] consteval auto explode_impl(Q, type_list<>, type_list<>) { return explode_result{dimensionless}; } template -[[nodiscard]] consteval auto explode(Q q) +[[nodiscard]] consteval auto explode_impl(Q q) { constexpr auto complexity = get_complexity(Q{}); if constexpr (complexity > Complexity) - return explode(q, type_list_sort{}, - type_list_sort{}); + return explode_impl(q, type_list_sort{}, + type_list_sort{}); else return explode_result{q}; } template -[[nodiscard]] consteval auto explode(Q q) +[[nodiscard]] consteval auto explode_impl(Q q) { constexpr auto complexity = get_complexity(Q{}); if constexpr (complexity > Complexity && requires { Q::_equation_; }) { @@ -803,6 +815,15 @@ template return explode_result{q}; } +template +constexpr auto explode_res = explode_impl(Q{}); + +template +[[nodiscard]] consteval auto explode(Q) +{ + return explode_res; +} + template [[nodiscard]] consteval specs_convertible_result are_ingredients_convertible(type_list num_from, @@ -889,10 +910,8 @@ extract_results(bool, From = {}, To = {}, prepend_rest = {}, Elem = {}) -> extra #endif -// tries to find the largest common power of a quantity -// in case powers have different factors of the same dimension, returns the remainder template -[[nodiscard]] consteval auto extract_convertible_quantities(From, To) +[[nodiscard]] consteval auto extract_convertible_quantities_impl(From, To) { constexpr auto qfrom = map_power(From{}); constexpr auto qto = map_power(To{}); @@ -925,6 +944,17 @@ template } } +template +constexpr auto extract_convertible_quantities_result = extract_convertible_quantities_impl(From{}, To{}); + +// tries to find the largest common power of a quantity +// in case powers have different factors of the same dimension, returns the remainder +template +[[nodiscard]] consteval auto extract_convertible_quantities(From, To) +{ + return extract_convertible_quantities_result; +} + enum class extracted_entities : std::int8_t { numerators, denominators, from, to }; template