#pragma once #include #include #include #include #include #include #include "openvic-simulation/utility/Utility.hpp" namespace OpenVic { struct ordered_container_string_hash { using is_transparent = void; [[nodiscard]] size_t operator()(const char* txt) const { return std::hash {}(txt); } [[nodiscard]] size_t operator()(std::string_view txt) const { return std::hash {}(txt); } [[nodiscard]] size_t operator()(const std::string& txt) const { return std::hash {}(txt); } }; template struct container_hash : std::hash {}; template<> struct container_hash : ordered_container_string_hash {}; template<> struct container_hash : ordered_container_string_hash {}; template<> struct container_hash : ordered_container_string_hash {}; // Useful for contiguous memory template< class Key, class T, class Hash = container_hash, class KeyEqual = std::equal_to<>, class Allocator = std::allocator>, class IndexType = std::uint_least32_t> using vector_ordered_map = tsl::ordered_map, Allocator>, IndexType>; // Useful for stable memory addresses (so long as you don't remove or insert values) template< class Key, class T, class Hash = container_hash, class KeyEqual = std::equal_to<>, class Allocator = std::allocator>, class IndexType = std::uint_least32_t> using deque_ordered_map = tsl::ordered_map, Allocator>, IndexType>; template< class Key, class T, class Hash = container_hash, class KeyEqual = std::equal_to<>, class Allocator = std::allocator>, class IndexType = std::uint_least32_t> using ordered_map = vector_ordered_map; // Useful for contiguous memory template< class Key, class Hash = container_hash, class KeyEqual = std::equal_to<>, class Allocator = std::allocator, class ValueTypeContainer = std::deque, class IndexType = std::uint_least32_t> using vector_ordered_set = tsl::ordered_set, IndexType>; // Useful for stable memory addresses (so long as you don't remove or insert values) template< class Key, class Hash = container_hash, class KeyEqual = std::equal_to<>, class Allocator = std::allocator, class ValueTypeContainer = std::deque, class IndexType = std::uint_least32_t> using deque_ordered_set = tsl::ordered_set, IndexType>; template< class Key, class Hash = container_hash, class KeyEqual = std::equal_to<>, class Allocator = std::allocator, class IndexType = std::uint_least32_t> using ordered_set = vector_ordered_set; template concept IsOrderedMap = utility::is_specialization_of_v; template concept IsOrderedSet = utility::is_specialization_of_v; template concept IsVectorOrderedMap = utility::is_specialization_of_v; template concept IsVectorOrderedSet = utility::is_specialization_of_v; template concept IsDequeOrderedMap = utility::is_specialization_of_v; template concept IsDequeOrderedSet = utility::is_specialization_of_v; template concept IsOrderedMapOf = IsOrderedMap && std::same_as && std::same_as; template concept IsOrderedSetOf = IsOrderedSet && std::same_as; template concept IsVectorOrderedMapOf = IsVectorOrderedMap && std::same_as && std::same_as; template concept IsVectorOrderedSetOf = IsVectorOrderedSet && std::same_as; template concept IsDequeOrderedMapOf = IsDequeOrderedMap && std::same_as && std::same_as; template concept IsDequeOrderedSetOf = IsDequeOrderedSet && std::same_as; }