diff --git a/develop/singles/headers/meta.hpp/meta_all.hpp b/develop/singles/headers/meta.hpp/meta_all.hpp index 596dd77..eafd365 100644 --- a/develop/singles/headers/meta.hpp/meta_all.hpp +++ b/develop/singles/headers/meta.hpp/meta_all.hpp @@ -513,6 +513,66 @@ namespace meta_hpp::detail }; } +namespace meta_hpp::detail +{ + class hashed_string final { + public: + hashed_string() = default; + ~hashed_string() = default; + + hashed_string(hashed_string&&) = default; + hashed_string(const hashed_string&) = default; + + hashed_string& operator=(hashed_string&&) = default; + hashed_string& operator=(const hashed_string&) = default; + + hashed_string(const char* str) noexcept + : hash_{std::hash{}(str)} {} + + hashed_string(std::string_view str) noexcept + : hash_{std::hash{}(str)} {} + + hashed_string(const std::string& str) noexcept + : hash_{std::hash{}(str)} {} + + void swap(hashed_string& other) noexcept { + std::swap(hash_, other.hash_); + } + + [[nodiscard]] std::size_t get_hash() const noexcept { + return hash_; + } + private: + std::size_t hash_{}; + }; + + inline void swap(hashed_string& l, hashed_string& r) noexcept { + l.swap(r); + } + + [[nodiscard]] inline bool operator<(hashed_string l, hashed_string r) noexcept { + return l.get_hash() < r.get_hash(); + } + + [[nodiscard]] inline bool operator==(hashed_string l, hashed_string r) noexcept { + return l.get_hash() == r.get_hash(); + } + + [[nodiscard]] inline bool operator!=(hashed_string l, hashed_string r) noexcept { + return l.get_hash() == r.get_hash(); + } +} + +namespace std +{ + template <> + struct hash { + size_t operator()(meta_hpp::detail::hashed_string hs) const noexcept { + return hs.get_hash(); + } + }; +} + namespace meta_hpp::detail { template < typename Key, typename Compare, typename Allocator > @@ -856,6 +916,7 @@ namespace meta_hpp::detail namespace meta_hpp { + using detail::hashed_string; using detail::memory_buffer; using detail::select_const; diff --git a/headers/meta.hpp/meta_base.hpp b/headers/meta.hpp/meta_base.hpp index 39b7da8..074df47 100644 --- a/headers/meta.hpp/meta_base.hpp +++ b/headers/meta.hpp/meta_base.hpp @@ -12,6 +12,7 @@ #include "meta_base/cvref_traits.hpp" #include "meta_base/fixed_function.hpp" #include "meta_base/hash_combiner.hpp" +#include "meta_base/hashed_string.hpp" #include "meta_base/insert_or_assign.hpp" #include "meta_base/is_in_place_type.hpp" #include "meta_base/memory_buffer.hpp" @@ -25,6 +26,7 @@ namespace meta_hpp { + using detail::hashed_string; using detail::memory_buffer; using detail::select_const; diff --git a/headers/meta.hpp/meta_base/hashed_string.hpp b/headers/meta.hpp/meta_base/hashed_string.hpp new file mode 100644 index 0000000..900a71a --- /dev/null +++ b/headers/meta.hpp/meta_base/hashed_string.hpp @@ -0,0 +1,69 @@ +/******************************************************************************* + * This file is part of the "https://github.com/blackmatov/meta.hpp" + * For conditions of distribution and use, see copyright notice in LICENSE.md + * Copyright (C) 2021-2023, by Matvey Cherevko (blackmatov@gmail.com) + ******************************************************************************/ + +#pragma once + +#include "base.hpp" + +namespace meta_hpp::detail +{ + class hashed_string final { + public: + hashed_string() = default; + ~hashed_string() = default; + + hashed_string(hashed_string&&) = default; + hashed_string(const hashed_string&) = default; + + hashed_string& operator=(hashed_string&&) = default; + hashed_string& operator=(const hashed_string&) = default; + + hashed_string(const char* str) noexcept + : hash_{std::hash{}(str)} {} + + hashed_string(std::string_view str) noexcept + : hash_{std::hash{}(str)} {} + + hashed_string(const std::string& str) noexcept + : hash_{std::hash{}(str)} {} + + void swap(hashed_string& other) noexcept { + std::swap(hash_, other.hash_); + } + + [[nodiscard]] std::size_t get_hash() const noexcept { + return hash_; + } + private: + std::size_t hash_{}; + }; + + inline void swap(hashed_string& l, hashed_string& r) noexcept { + l.swap(r); + } + + [[nodiscard]] inline bool operator<(hashed_string l, hashed_string r) noexcept { + return l.get_hash() < r.get_hash(); + } + + [[nodiscard]] inline bool operator==(hashed_string l, hashed_string r) noexcept { + return l.get_hash() == r.get_hash(); + } + + [[nodiscard]] inline bool operator!=(hashed_string l, hashed_string r) noexcept { + return l.get_hash() == r.get_hash(); + } +} + +namespace std +{ + template <> + struct hash { + size_t operator()(meta_hpp::detail::hashed_string hs) const noexcept { + return hs.get_hash(); + } + }; +}