diff --git a/include/glaze/mustache/mustache.hpp b/include/glaze/mustache/mustache.hpp index 4732366617..6f33be9f3e 100644 --- a/include/glaze/mustache/mustache.hpp +++ b/include/glaze/mustache/mustache.hpp @@ -66,7 +66,7 @@ namespace glz return unexpected( error_ctx{ctx.error, ctx.custom_error_message, size_t(it - start), ctx.includer_error}); } - else { + else [[likely]] { static thread_local std::string temp{}; detail::jump_table( [&]() { diff --git a/include/glaze/mustache/stencilcount.hpp b/include/glaze/mustache/stencilcount.hpp index 217f08bc43..46349085a2 100644 --- a/include/glaze/mustache/stencilcount.hpp +++ b/include/glaze/mustache/stencilcount.hpp @@ -87,50 +87,49 @@ namespace glz break; } - auto s = it; + auto start = it; while (it != end && *it != '}' && *it != ' ' && *it != '\t') { ++it; } - const sv key{s, size_t(it - s)}; + const sv key{start, size_t(it - start)}; skip_whitespace(); - static constexpr auto num_members = refl.N; - - decltype(auto) frozen_map = [&]() -> decltype(auto) { - using V = decay_keep_volatile_t; - if constexpr (detail::reflectable && num_members > 0) { -#if ((defined _MSC_VER) && (!defined __clang__)) - static thread_local auto cmap = detail::make_map(); -#else - static thread_local constinit auto cmap = detail::make_map(); -#endif - // We want to run this populate outside of the while loop - populate_map(value, cmap); // Function required for MSVC to build - return cmap; - } - else if constexpr (detail::glaze_object_t && num_members > 0) { - static constexpr auto cmap = detail::make_map(); - return cmap; - } - else { - return nullptr; - } - }(); - - if (const auto& member_it = frozen_map.find(key); member_it != frozen_map.end()) [[likely]] { - std::visit( - [&](auto&& member_ptr) { - static thread_local std::string temp{}; - std::ignore = - write>(detail::get_member(value, member_ptr), temp, ctx); - result.append(temp); + static constexpr auto N = refl.N; + static constexpr auto HashInfo = detail::hash_info; + + const auto index = + detail::decode_hash_with_size::op(start, end, key.size()); + + if (index < N) [[likely]] { + static thread_local std::string temp{}; + detail::jump_table( + [&]() { + static constexpr auto TargetKey = get(refl.keys); + static constexpr auto Length = TargetKey.size(); + if ((Length == key.size()) && compare(TargetKey.data(), start)) [[likely]] { + if constexpr (detail::reflectable && N > 0) { + std::ignore = + write>(detail::get_member(value, get(detail::to_tuple(value))), temp, ctx); + } + else if constexpr (detail::glaze_object_t && N > 0) { + std::ignore = + write>(detail::get_member(value, get(refl.values)), temp, ctx); + } + } + else { + ctx.error = error_code::unknown_key; + } }, - member_it->second); - if (bool(ctx.error)) [[unlikely]] + index); + + if (bool(ctx.error)) [[unlikely]] { return unexpected( error_ctx{ctx.error, ctx.custom_error_message, size_t(it - start), ctx.includer_error}); + } + + result.append(temp); } else { // TODO: Is this an error?