From abe42e1edc7582b6d12842e79c23288c8e1e507e Mon Sep 17 00:00:00 2001 From: BlackMATov Date: Sun, 12 Mar 2023 01:11:31 +0700 Subject: [PATCH] replace state's sets to vectors for order --- develop/singles/headers/meta.hpp/meta_all.hpp | 216 +++++++-------- .../untests/meta_base/insert_or_assign.cpp | 246 ------------------ .../untests/meta_types/class_type_tests.cpp | 16 +- headers/meta.hpp/meta_base.hpp | 23 +- .../meta.hpp/meta_base/insert_or_assign.hpp | 56 ++-- headers/meta.hpp/meta_binds/class_bind.hpp | 34 +-- headers/meta.hpp/meta_states.hpp | 8 +- headers/meta.hpp/meta_states/scope.hpp | 4 +- headers/meta.hpp/meta_types.hpp | 41 +-- headers/meta.hpp/meta_types/class_type.hpp | 48 ++-- headers/meta.hpp/meta_types/enum_type.hpp | 2 +- 11 files changed, 204 insertions(+), 490 deletions(-) delete mode 100644 develop/untests/meta_base/insert_or_assign.cpp diff --git a/develop/singles/headers/meta.hpp/meta_all.hpp b/develop/singles/headers/meta.hpp/meta_all.hpp index fe2d58f..d5b2b19 100644 --- a/develop/singles/headers/meta.hpp/meta_all.hpp +++ b/develop/singles/headers/meta.hpp/meta_all.hpp @@ -958,54 +958,30 @@ namespace std namespace meta_hpp::detail { - template < typename Key, typename Compare, typename Allocator > - requires std::is_move_constructible_v && std::is_move_assignable_v - typename std::set::iterator insert_or_assign( // - std::set& set, - typename std::set::value_type&& value + template < typename Value, typename Allocator > + requires std::is_move_constructible_v && std::is_move_assignable_v + typename std::vector::iterator insert_or_assign( // + std::vector& vector, + typename std::vector::value_type&& value ) { - auto&& [position, inserted] = set.insert(std::move(value)); - - if ( inserted ) { + if ( auto&& position{std::find(vector.begin(), vector.end(), value)}; position != vector.end() ) { + *position = std::move(value); return position; } - - auto node = set.extract(position++); - - META_HPP_TRY { - node.value() = std::move(value); - } - META_HPP_CATCH(...) { - set.insert(position, std::move(node)); - META_HPP_RETHROW(); - } - - return set.insert(position, std::move(node)); + return vector.insert(vector.end(), std::move(value)); } - template < typename Key, typename Compare, typename Allocator > - requires std::is_copy_constructible_v && std::is_copy_assignable_v - typename std::set::iterator insert_or_assign( // - std::set& set, - const typename std::set::value_type& value + template < typename Value, typename Allocator > + requires std::is_copy_constructible_v && std::is_copy_assignable_v + typename std::vector::iterator insert_or_assign( // + std::vector& vector, + const typename std::vector::value_type& value ) { - auto&& [position, inserted] = set.insert(value); - - if ( inserted ) { + if ( auto&& position{std::find(vector.begin(), vector.end(), value)}; position != vector.end() ) { + *position = value; return position; } - - auto node = set.extract(position++); - - META_HPP_TRY { - node.value() = value; - } - META_HPP_CATCH(...) { - set.insert(position, std::move(node)); - META_HPP_RETHROW(); - } - - return set.insert(position, std::move(node)); + return vector.insert(vector.end(), value); } } @@ -1817,24 +1793,23 @@ namespace meta_hpp namespace meta_hpp { - using any_type_list = std::vector; - using argument_list = std::vector; using string_ilist = std::initializer_list; using metadata_map = std::map>; using typedef_map = std::map>; - using class_set = std::set>; - using enum_set = std::set>; + using class_list = std::vector; + using enum_list = std::vector; - using constructor_set = std::set>; - using destructor_set = std::set>; - using evalue_set = std::set>; - using function_set = std::set>; - using member_set = std::set>; - using method_set = std::set>; - using scope_set = std::set>; - using variable_set = std::set>; + using any_type_list = std::vector; + using argument_list = std::vector; + using constructor_list = std::vector; + using destructor_list = std::vector; + using evalue_list = std::vector; + using function_list = std::vector; + using member_list = std::vector; + using method_list = std::vector; + using variable_list = std::vector; } namespace meta_hpp::detail @@ -2614,15 +2589,15 @@ namespace meta_hpp [[nodiscard]] any_type get_argument_type(std::size_t position) const noexcept; [[nodiscard]] const any_type_list& get_argument_types() const noexcept; - [[nodiscard]] const class_set& get_base_classes() const noexcept; - [[nodiscard]] const class_set& get_derived_classes() const noexcept; - [[nodiscard]] const constructor_set& get_constructors() const noexcept; - [[nodiscard]] const destructor_set& get_destructors() const noexcept; - [[nodiscard]] const function_set& get_functions() const noexcept; - [[nodiscard]] const member_set& get_members() const noexcept; - [[nodiscard]] const method_set& get_methods() const noexcept; + [[nodiscard]] const class_list& get_base_classes() const noexcept; + [[nodiscard]] const class_list& get_derived_classes() const noexcept; + [[nodiscard]] const constructor_list& get_constructors() const noexcept; + [[nodiscard]] const destructor_list& get_destructors() const noexcept; + [[nodiscard]] const function_list& get_functions() const noexcept; + [[nodiscard]] const member_list& get_members() const noexcept; + [[nodiscard]] const method_list& get_methods() const noexcept; [[nodiscard]] const typedef_map& get_typedefs() const noexcept; - [[nodiscard]] const variable_set& get_variables() const noexcept; + [[nodiscard]] const variable_list& get_variables() const noexcept; template < typename... Args > [[nodiscard]] uvalue create(Args&&... args) const; @@ -2751,7 +2726,7 @@ namespace meta_hpp [[nodiscard]] number_type get_underlying_type() const noexcept; - [[nodiscard]] const evalue_set& get_evalues() const noexcept; + [[nodiscard]] const evalue_list& get_evalues() const noexcept; [[nodiscard]] evalue get_evalue(std::string_view name) const noexcept; @@ -2901,15 +2876,15 @@ namespace meta_hpp::detail const std::size_t align; const any_type_list argument_types; - class_set base_classes; - class_set derived_classes; - constructor_set constructors; - destructor_set destructors; - function_set functions; - member_set members; - method_set methods; + class_list base_classes; + class_list derived_classes; + constructor_list constructors; + destructor_list destructors; + function_list functions; + member_list members; + method_list methods; typedef_map typedefs; - variable_set variables; + variable_list variables; struct upcast_func_t final { using upcast_t = void* (*)(void*); @@ -2928,13 +2903,14 @@ namespace meta_hpp::detail struct upcast_func_list_t final { using upcasts_t = std::vector; + using vbases_t = std::set>; upcasts_t upcasts{}; - class_set vbases{}; + vbases_t vbases{}; bool is_ambiguous{}; upcast_func_list_t(const upcast_func_t& _upcast); - upcast_func_list_t(upcasts_t _upcasts, class_set _vbases); + upcast_func_list_t(upcasts_t _upcasts, vbases_t _vbases); [[nodiscard]] void* apply(void* ptr) const noexcept; [[nodiscard]] const void* apply(const void* ptr) const noexcept; @@ -2973,7 +2949,7 @@ namespace meta_hpp::detail const enum_bitflags flags; const number_type underlying_type; - evalue_set evalues; + evalue_list evalues; template < enum_kind Enum > explicit enum_type_data(type_list); @@ -3896,9 +3872,9 @@ namespace meta_hpp [[nodiscard]] const std::string& get_name() const noexcept; - [[nodiscard]] const function_set& get_functions() const noexcept; + [[nodiscard]] const function_list& get_functions() const noexcept; [[nodiscard]] const typedef_map& get_typedefs() const noexcept; - [[nodiscard]] const variable_set& get_variables() const noexcept; + [[nodiscard]] const variable_list& get_variables() const noexcept; [[nodiscard]] function get_function(std::string_view name) const noexcept; [[nodiscard]] any_type get_typedef(std::string_view name) const noexcept; @@ -4111,9 +4087,9 @@ namespace meta_hpp::detail scope_index index; metadata_map metadata; - function_set functions{}; + function_list functions{}; typedef_map typedefs{}; - variable_set variables{}; + variable_list variables{}; [[nodiscard]] static scope_state_ptr make(std::string name, metadata_map metadata); explicit scope_state(scope_index index, metadata_map metadata); @@ -4906,19 +4882,27 @@ namespace meta_hpp::detail::class_bind_impl using upcast_func_t = class_type_data::upcast_func_t; using upcast_func_list_t = class_type_data::upcast_func_list_t; - using new_bases_db_t = std::map; + using new_bases_db_t = std::vector>; using deep_upcasts_db_t = std::map>; - using derived_classes_db_t = std::map>; + using derived_classes_db_t = std::map>; template < class_kind Class, class_kind Base > requires std::is_base_of_v void update_new_bases_db( // new_bases_db_t& new_bases_db ) { - new_bases_db.try_emplace( // - resolve_type(), - std::in_place_type, - std::in_place_type); + const class_type& new_base = resolve_type(); + + for ( auto&& [db_base, _] : new_bases_db ) { + if ( db_base == new_base ) { + return; + } + } + + new_bases_db.emplace_back( // + new_base, + upcast_func_t{std::in_place_type, std::in_place_type} + ); } inline void update_deep_upcasts_db( // @@ -4961,8 +4945,8 @@ namespace meta_hpp::detail::class_bind_impl derived_classes_db_t& derived_classes_db ) { const class_type_data& base_class_data = *type_access(new_base_class); - class_set new_derived_classes{base_class_data.derived_classes}; - new_derived_classes.emplace(self_class); + class_list new_derived_classes{base_class_data.derived_classes}; + insert_or_assign(new_derived_classes, self_class); derived_classes_db.emplace(new_base_class, std::move(new_derived_classes)); } } @@ -4988,28 +4972,24 @@ namespace meta_hpp using namespace detail; using namespace detail::class_bind_impl; - if ( (... && get_data().base_classes.contains(resolve_type())) ) { - return *this; - } - new_bases_db_t new_bases_db; (update_new_bases_db(new_bases_db), ...); deep_upcasts_db_t deep_upcasts_db; derived_classes_db_t derived_classes_db; - class_set new_base_classes{get_data().base_classes}; + class_list new_base_classes{get_data().base_classes}; base_upcasts_t new_base_upcasts{get_data().base_upcasts}; for ( auto&& [new_base_class, self_to_new_base] : new_bases_db ) { - if ( new_base_classes.contains(new_base_class) ) { + if ( std::find(new_base_classes.begin(), new_base_classes.end(), new_base_class) != new_base_classes.end() ) { continue; } update_deep_upcasts_db(*this, new_base_class, self_to_new_base, deep_upcasts_db); updata_derived_classes_db(*this, new_base_class, derived_classes_db); - new_base_classes.emplace(new_base_class); + new_base_classes.emplace_back(new_base_class); new_base_upcasts.emplace(new_base_class, self_to_new_base); } @@ -7880,7 +7860,7 @@ namespace meta_hpp return data_->underlying_type; } - inline const evalue_set& enum_type::get_evalues() const noexcept { + inline const evalue_list& enum_type::get_evalues() const noexcept { return data_->evalues; } @@ -8195,7 +8175,7 @@ namespace meta_hpp::detail } } - inline class_type_data::upcast_func_list_t::upcast_func_list_t(upcasts_t _upcasts, class_set _vbases) + inline class_type_data::upcast_func_list_t::upcast_func_list_t(upcasts_t _upcasts, vbases_t _vbases) : upcasts{std::move(_upcasts)} , vbases{std::move(_vbases)} {} @@ -8220,7 +8200,7 @@ namespace meta_hpp::detail new_upcasts.insert(new_upcasts.end(), l.upcasts.begin(), l.upcasts.end()); new_upcasts.insert(new_upcasts.end(), r.upcasts.begin(), r.upcasts.end()); - class_set new_vbases; + class_type_data::upcast_func_list_t::vbases_t new_vbases; new_vbases.insert(l.vbases.begin(), l.vbases.end()); new_vbases.insert(r.vbases.begin(), r.vbases.end()); @@ -8254,31 +8234,31 @@ namespace meta_hpp return data_->argument_types; } - inline const class_set& class_type::get_base_classes() const noexcept { + inline const class_list& class_type::get_base_classes() const noexcept { return data_->base_classes; } - inline const class_set& class_type::get_derived_classes() const noexcept { + inline const class_list& class_type::get_derived_classes() const noexcept { return data_->derived_classes; } - inline const constructor_set& class_type::get_constructors() const noexcept { + inline const constructor_list& class_type::get_constructors() const noexcept { return data_->constructors; } - inline const destructor_set& class_type::get_destructors() const noexcept { + inline const destructor_list& class_type::get_destructors() const noexcept { return data_->destructors; } - inline const function_set& class_type::get_functions() const noexcept { + inline const function_list& class_type::get_functions() const noexcept { return data_->functions; } - inline const member_set& class_type::get_members() const noexcept { + inline const member_list& class_type::get_members() const noexcept { return data_->members; } - inline const method_set& class_type::get_methods() const noexcept { + inline const method_list& class_type::get_methods() const noexcept { return data_->methods; } @@ -8286,7 +8266,7 @@ namespace meta_hpp return data_->typedefs; } - inline const variable_set& class_type::get_variables() const noexcept { + inline const variable_list& class_type::get_variables() const noexcept { return data_->variables; } @@ -8402,8 +8382,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const function& function = base.get_function(name, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const function& function = iter->get_function(name, recursively) ) { return function; } } @@ -8420,8 +8400,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const member& member = base.get_member(name, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const member& member = iter->get_member(name, recursively) ) { return member; } } @@ -8438,8 +8418,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const method& method = base.get_method(name, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const method& method = iter->get_method(name, recursively) ) { return method; } } @@ -8454,8 +8434,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const any_type& type = base.get_typedef(name, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const any_type& type = iter->get_typedef(name, recursively) ) { return type; } } @@ -8472,8 +8452,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const variable& variable = base.get_variable(name, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const variable& variable = iter->get_variable(name, recursively) ) { return variable; } } @@ -8554,8 +8534,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const function& function = base.get_function_with(name, first, last, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const function& function = iter->get_function_with(name, first, last, recursively) ) { return function; } } @@ -8612,8 +8592,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const method& method = base.get_method_with(name, first, last, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const method& method = iter->get_method_with(name, first, last, recursively) ) { return method; } } @@ -8657,7 +8637,7 @@ namespace meta_hpp return state_->index.get_name(); } - inline const function_set& scope::get_functions() const noexcept { + inline const function_list& scope::get_functions() const noexcept { return state_->functions; } @@ -8665,7 +8645,7 @@ namespace meta_hpp return state_->typedefs; } - inline const variable_set& scope::get_variables() const noexcept { + inline const variable_list& scope::get_variables() const noexcept { return state_->variables; } diff --git a/develop/untests/meta_base/insert_or_assign.cpp b/develop/untests/meta_base/insert_or_assign.cpp deleted file mode 100644 index ddb9da8..0000000 --- a/develop/untests/meta_base/insert_or_assign.cpp +++ /dev/null @@ -1,246 +0,0 @@ -/******************************************************************************* - * 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) - ******************************************************************************/ - -#include -#include - -namespace -{ - struct movable_value { - int key{}; - int data{}; - - movable_value(int k, int d) : key{k}, data{d} {} - - [[maybe_unused]] movable_value(movable_value&&) = default; - [[maybe_unused]] movable_value& operator=(movable_value&&) = default; - - movable_value(const movable_value&) = delete; - movable_value& operator=(const movable_value&) = delete; - - [[maybe_unused]] - friend bool operator<(const movable_value& l, const movable_value& r) noexcept { - return l.key < r.key; - } - - [[maybe_unused]] - friend bool operator==(const movable_value& l, const movable_value& r) noexcept { - return l.key == r.key && l.data == r.data; - } - }; - - struct copyable_value { - int key{}; - int data{}; - - [[maybe_unused]] - friend bool operator<(const copyable_value& l, const copyable_value& r) noexcept { - return l.key < r.key; - } - - [[maybe_unused]] - friend bool operator==(const copyable_value& l, const copyable_value& r) noexcept { - return l.key == r.key && l.data == r.data; - } - }; - - struct exception_on_move_value { - int key{}; - int data{}; - - exception_on_move_value(int k, int d) - : key{k} - , data{d} {} - - exception_on_move_value(const exception_on_move_value&) = default; - exception_on_move_value& operator=(const exception_on_move_value&) = default; - - exception_on_move_value(exception_on_move_value&& other) - : key{other.key} - , data{other.data} { - if ( other.data != 42 ) { - other.key = 0; - other.data = 0; - return; - } - #if !defined(META_HPP_NO_EXCEPTIONS) - throw std::exception{}; - #else - std::abort(); - #endif - } - - exception_on_move_value& operator=(exception_on_move_value&& other) { - if ( this == &other ) { - return *this; - } - - if ( other.data != 42 ) { - key = other.key; - data = other.data; - return *this; - } - - #if !defined(META_HPP_NO_EXCEPTIONS) - throw std::exception{}; - #else - std::abort(); - #endif - } - - [[maybe_unused]] - friend bool operator<(const exception_on_move_value& l, const exception_on_move_value& r) noexcept { - return l.key < r.key; - } - - [[maybe_unused]] - friend bool operator==(const exception_on_move_value& l, const exception_on_move_value& r) noexcept { - return l.key == r.key && l.data == r.data; - } - }; - - struct exception_on_copy_value { - int key{}; - int data{}; - - exception_on_copy_value(int k, int d) - : key{k} - , data{d} {} - - exception_on_copy_value(exception_on_copy_value&& other) = default; - exception_on_copy_value& operator=(exception_on_copy_value&& other) = default; - - exception_on_copy_value(const exception_on_copy_value& other) - : key{other.key} - , data{other.data} { - if ( other.data != 42 ) { - return; - } - #if !defined(META_HPP_NO_EXCEPTIONS) - throw std::exception{}; - #else - std::abort(); - #endif - } - - exception_on_copy_value& operator=(const exception_on_copy_value& other) { - if ( this == &other ) { - return *this; - } - - if ( other.data != 42 ) { - key = other.key; - data = other.data; - return *this; - } - - #if !defined(META_HPP_NO_EXCEPTIONS) - throw std::exception{}; - #else - std::abort(); - #endif - } - - [[maybe_unused]] - friend bool operator<(const exception_on_copy_value& l, const exception_on_copy_value& r) noexcept { - return l.key < r.key; - } - - [[maybe_unused]] - friend bool operator==(const exception_on_copy_value& l, const exception_on_copy_value& r) noexcept { - return l.key == r.key && l.data == r.data; - } - }; -} - -TEST_CASE("meta/meta_base/insert_or_assign") { - namespace meta = meta_hpp; - using meta::detail::insert_or_assign; - - SUBCASE("movable_value/insert") { - std::set> s; - s.insert({1, 10}); - s.insert({3, 30}); - CHECK(*insert_or_assign(s, movable_value{2, 20}) == movable_value{2, 20}); - { - std::set> s2; - s2.insert({1, 10}); - s2.insert({2, 20}); - s2.insert({3, 30}); - CHECK(s == s2); - } - } - - SUBCASE("movable_value/replace") { - std::set> s; - s.insert({1, 10}); - s.insert({3, 30}); - CHECK(*insert_or_assign(s, movable_value{3, 42}) == movable_value{3, 42}); - { - std::set> s2; - s2.insert({1, 10}); - s2.insert({3, 42}); - CHECK(s == s2); - } - } - - SUBCASE("copyable_value/insert/0") { - std::set> s{{1, 10}, {3, 30}}; - CHECK(*insert_or_assign(s, copyable_value{2, 20}) == copyable_value{2, 20}); - CHECK(s == std::set>{{1, 10}, {2, 20}, {3, 30}}); - } - - SUBCASE("copyable_value/insert/1") { - std::set> s{{1, 10}, {3, 30}}; - copyable_value v{2, 20}; - CHECK(*insert_or_assign(s, v) == v); - CHECK(s == std::set>{{1, 10}, {2, 20}, {3, 30}}); - } - - SUBCASE("copyable_value/replace/0") { - std::set> s{{1, 10}, {3, 30}}; - CHECK(*insert_or_assign(s, copyable_value{3, 42}) == copyable_value{3, 42}); - CHECK(s == std::set>{{1, 10}, {3, 42}}); - } - - SUBCASE("copyable_value/replace/1") { - std::set> s{{1, 10}, {3, 30}}; - copyable_value v{3, 42}; - CHECK(*insert_or_assign(s, v) == v); - CHECK(s == std::set>{{1, 10}, {3, 42}}); - } -} - -TEST_CASE("meta/meta_base/insert_or_assign/exceptions") { - namespace meta = meta_hpp; - using meta::detail::insert_or_assign; - - SUBCASE("on_move/insert") { - std::set> s{{1, 10}, {3, 30}}; - CHECK_THROWS(insert_or_assign(s, exception_on_move_value{2, 42})); - CHECK(s == std::set>{{1, 10}, {3, 30}}); - } - - SUBCASE("on_move/replace") { - std::set> s{{1, 10}, {3, 30}}; - CHECK_THROWS(insert_or_assign(s, exception_on_move_value{3, 42})); - CHECK(s == std::set>{{1, 10}, {3, 30}}); - } - - SUBCASE("on_copy/insert") { - std::set> s{{1, 10}, {3, 30}}; - exception_on_copy_value v{2, 42}; - CHECK_THROWS(insert_or_assign(s, v)); - CHECK(s == std::set>{{1, 10}, {3, 30}}); - } - - SUBCASE("on_copy/replace") { - std::set> s{{1, 10}, {3, 30}}; - exception_on_copy_value v{3, 42}; - CHECK_THROWS(insert_or_assign(s, v)); - CHECK(s == std::set>{{1, 10}, {3, 30}}); - } -} diff --git a/develop/untests/meta_types/class_type_tests.cpp b/develop/untests/meta_types/class_type_tests.cpp index 577a3bd..904f1f2 100644 --- a/develop/untests/meta_types/class_type_tests.cpp +++ b/develop/untests/meta_types/class_type_tests.cpp @@ -203,17 +203,17 @@ TEST_CASE("meta/meta_types/class_type") { } SUBCASE("get_base_classes") { - CHECK(base_clazz_1_type.get_base_classes() == meta::class_set{}); - CHECK(base_clazz_2_type.get_base_classes() == meta::class_set{}); - CHECK(derived_clazz_type.get_base_classes() == meta::class_set{base_clazz_1_type, base_clazz_2_type}); - CHECK(final_derived_clazz_type.get_base_classes() == meta::class_set{derived_clazz_type}); + CHECK(base_clazz_1_type.get_base_classes() == meta::class_list{}); + CHECK(base_clazz_2_type.get_base_classes() == meta::class_list{}); + CHECK(derived_clazz_type.get_base_classes() == meta::class_list{base_clazz_1_type, base_clazz_2_type}); + CHECK(final_derived_clazz_type.get_base_classes() == meta::class_list{derived_clazz_type}); } SUBCASE("get_derived_classes") { - CHECK(base_clazz_1_type.get_derived_classes() == meta::class_set{derived_clazz_type}); - CHECK(base_clazz_2_type.get_derived_classes() == meta::class_set{derived_clazz_type}); - CHECK(derived_clazz_type.get_derived_classes() == meta::class_set{final_derived_clazz_type}); - CHECK(final_derived_clazz_type.get_derived_classes() == meta::class_set{}); + CHECK(base_clazz_1_type.get_derived_classes() == meta::class_list{derived_clazz_type}); + CHECK(base_clazz_2_type.get_derived_classes() == meta::class_list{derived_clazz_type}); + CHECK(derived_clazz_type.get_derived_classes() == meta::class_list{final_derived_clazz_type}); + CHECK(final_derived_clazz_type.get_derived_classes() == meta::class_list{}); } SUBCASE("get_functions") { diff --git a/headers/meta.hpp/meta_base.hpp b/headers/meta.hpp/meta_base.hpp index 009c6ef..8409d96 100644 --- a/headers/meta.hpp/meta_base.hpp +++ b/headers/meta.hpp/meta_base.hpp @@ -217,22 +217,21 @@ namespace meta_hpp namespace meta_hpp { - using any_type_list = std::vector; - using argument_list = std::vector; using string_ilist = std::initializer_list; using metadata_map = std::map>; using typedef_map = std::map>; - using class_set = std::set>; - using enum_set = std::set>; + using class_list = std::vector; + using enum_list = std::vector; - using constructor_set = std::set>; - using destructor_set = std::set>; - using evalue_set = std::set>; - using function_set = std::set>; - using member_set = std::set>; - using method_set = std::set>; - using scope_set = std::set>; - using variable_set = std::set>; + using any_type_list = std::vector; + using argument_list = std::vector; + using constructor_list = std::vector; + using destructor_list = std::vector; + using evalue_list = std::vector; + using function_list = std::vector; + using member_list = std::vector; + using method_list = std::vector; + using variable_list = std::vector; } diff --git a/headers/meta.hpp/meta_base/insert_or_assign.hpp b/headers/meta.hpp/meta_base/insert_or_assign.hpp index f01ddfc..958dc15 100644 --- a/headers/meta.hpp/meta_base/insert_or_assign.hpp +++ b/headers/meta.hpp/meta_base/insert_or_assign.hpp @@ -11,54 +11,30 @@ namespace meta_hpp::detail { - template < typename Key, typename Compare, typename Allocator > - requires std::is_move_constructible_v && std::is_move_assignable_v - typename std::set::iterator insert_or_assign( // - std::set& set, - typename std::set::value_type&& value + template < typename Value, typename Allocator > + requires std::is_move_constructible_v && std::is_move_assignable_v + typename std::vector::iterator insert_or_assign( // + std::vector& vector, + typename std::vector::value_type&& value ) { - auto&& [position, inserted] = set.insert(std::move(value)); - - if ( inserted ) { + if ( auto&& position{std::find(vector.begin(), vector.end(), value)}; position != vector.end() ) { + *position = std::move(value); return position; } - - auto node = set.extract(position++); - - META_HPP_TRY { - node.value() = std::move(value); - } - META_HPP_CATCH(...) { - set.insert(position, std::move(node)); - META_HPP_RETHROW(); - } - - return set.insert(position, std::move(node)); + return vector.insert(vector.end(), std::move(value)); } - template < typename Key, typename Compare, typename Allocator > - requires std::is_copy_constructible_v && std::is_copy_assignable_v - typename std::set::iterator insert_or_assign( // - std::set& set, - const typename std::set::value_type& value + template < typename Value, typename Allocator > + requires std::is_copy_constructible_v && std::is_copy_assignable_v + typename std::vector::iterator insert_or_assign( // + std::vector& vector, + const typename std::vector::value_type& value ) { - auto&& [position, inserted] = set.insert(value); - - if ( inserted ) { + if ( auto&& position{std::find(vector.begin(), vector.end(), value)}; position != vector.end() ) { + *position = value; return position; } - - auto node = set.extract(position++); - - META_HPP_TRY { - node.value() = value; - } - META_HPP_CATCH(...) { - set.insert(position, std::move(node)); - META_HPP_RETHROW(); - } - - return set.insert(position, std::move(node)); + return vector.insert(vector.end(), value); } } diff --git a/headers/meta.hpp/meta_binds/class_bind.hpp b/headers/meta.hpp/meta_binds/class_bind.hpp index 2419364..8e22436 100644 --- a/headers/meta.hpp/meta_binds/class_bind.hpp +++ b/headers/meta.hpp/meta_binds/class_bind.hpp @@ -18,19 +18,27 @@ namespace meta_hpp::detail::class_bind_impl using upcast_func_t = class_type_data::upcast_func_t; using upcast_func_list_t = class_type_data::upcast_func_list_t; - using new_bases_db_t = std::map; + using new_bases_db_t = std::vector>; using deep_upcasts_db_t = std::map>; - using derived_classes_db_t = std::map>; + using derived_classes_db_t = std::map>; template < class_kind Class, class_kind Base > requires std::is_base_of_v void update_new_bases_db( // new_bases_db_t& new_bases_db ) { - new_bases_db.try_emplace( // - resolve_type(), - std::in_place_type, - std::in_place_type); + const class_type& new_base = resolve_type(); + + for ( auto&& [db_base, _] : new_bases_db ) { + if ( db_base == new_base ) { + return; + } + } + + new_bases_db.emplace_back( // + new_base, + upcast_func_t{std::in_place_type, std::in_place_type} + ); } inline void update_deep_upcasts_db( // @@ -73,8 +81,8 @@ namespace meta_hpp::detail::class_bind_impl derived_classes_db_t& derived_classes_db ) { const class_type_data& base_class_data = *type_access(new_base_class); - class_set new_derived_classes{base_class_data.derived_classes}; - new_derived_classes.emplace(self_class); + class_list new_derived_classes{base_class_data.derived_classes}; + insert_or_assign(new_derived_classes, self_class); derived_classes_db.emplace(new_base_class, std::move(new_derived_classes)); } } @@ -100,28 +108,24 @@ namespace meta_hpp using namespace detail; using namespace detail::class_bind_impl; - if ( (... && get_data().base_classes.contains(resolve_type())) ) { - return *this; - } - new_bases_db_t new_bases_db; (update_new_bases_db(new_bases_db), ...); deep_upcasts_db_t deep_upcasts_db; derived_classes_db_t derived_classes_db; - class_set new_base_classes{get_data().base_classes}; + class_list new_base_classes{get_data().base_classes}; base_upcasts_t new_base_upcasts{get_data().base_upcasts}; for ( auto&& [new_base_class, self_to_new_base] : new_bases_db ) { - if ( new_base_classes.contains(new_base_class) ) { + if ( std::find(new_base_classes.begin(), new_base_classes.end(), new_base_class) != new_base_classes.end() ) { continue; } update_deep_upcasts_db(*this, new_base_class, self_to_new_base, deep_upcasts_db); updata_derived_classes_db(*this, new_base_class, derived_classes_db); - new_base_classes.emplace(new_base_class); + new_base_classes.emplace_back(new_base_class); new_base_upcasts.emplace(new_base_class, self_to_new_base); } diff --git a/headers/meta.hpp/meta_states.hpp b/headers/meta.hpp/meta_states.hpp index ab3970a..abc162d 100644 --- a/headers/meta.hpp/meta_states.hpp +++ b/headers/meta.hpp/meta_states.hpp @@ -326,9 +326,9 @@ namespace meta_hpp [[nodiscard]] const std::string& get_name() const noexcept; - [[nodiscard]] const function_set& get_functions() const noexcept; + [[nodiscard]] const function_list& get_functions() const noexcept; [[nodiscard]] const typedef_map& get_typedefs() const noexcept; - [[nodiscard]] const variable_set& get_variables() const noexcept; + [[nodiscard]] const variable_list& get_variables() const noexcept; [[nodiscard]] function get_function(std::string_view name) const noexcept; [[nodiscard]] any_type get_typedef(std::string_view name) const noexcept; @@ -541,9 +541,9 @@ namespace meta_hpp::detail scope_index index; metadata_map metadata; - function_set functions{}; + function_list functions{}; typedef_map typedefs{}; - variable_set variables{}; + variable_list variables{}; [[nodiscard]] static scope_state_ptr make(std::string name, metadata_map metadata); explicit scope_state(scope_index index, metadata_map metadata); diff --git a/headers/meta.hpp/meta_states/scope.hpp b/headers/meta.hpp/meta_states/scope.hpp index a1d4403..d80f262 100644 --- a/headers/meta.hpp/meta_states/scope.hpp +++ b/headers/meta.hpp/meta_states/scope.hpp @@ -34,7 +34,7 @@ namespace meta_hpp return state_->index.get_name(); } - inline const function_set& scope::get_functions() const noexcept { + inline const function_list& scope::get_functions() const noexcept { return state_->functions; } @@ -42,7 +42,7 @@ namespace meta_hpp return state_->typedefs; } - inline const variable_set& scope::get_variables() const noexcept { + inline const variable_list& scope::get_variables() const noexcept { return state_->variables; } diff --git a/headers/meta.hpp/meta_types.hpp b/headers/meta.hpp/meta_types.hpp index d086133..270df21 100644 --- a/headers/meta.hpp/meta_types.hpp +++ b/headers/meta.hpp/meta_types.hpp @@ -184,15 +184,15 @@ namespace meta_hpp [[nodiscard]] any_type get_argument_type(std::size_t position) const noexcept; [[nodiscard]] const any_type_list& get_argument_types() const noexcept; - [[nodiscard]] const class_set& get_base_classes() const noexcept; - [[nodiscard]] const class_set& get_derived_classes() const noexcept; - [[nodiscard]] const constructor_set& get_constructors() const noexcept; - [[nodiscard]] const destructor_set& get_destructors() const noexcept; - [[nodiscard]] const function_set& get_functions() const noexcept; - [[nodiscard]] const member_set& get_members() const noexcept; - [[nodiscard]] const method_set& get_methods() const noexcept; + [[nodiscard]] const class_list& get_base_classes() const noexcept; + [[nodiscard]] const class_list& get_derived_classes() const noexcept; + [[nodiscard]] const constructor_list& get_constructors() const noexcept; + [[nodiscard]] const destructor_list& get_destructors() const noexcept; + [[nodiscard]] const function_list& get_functions() const noexcept; + [[nodiscard]] const member_list& get_members() const noexcept; + [[nodiscard]] const method_list& get_methods() const noexcept; [[nodiscard]] const typedef_map& get_typedefs() const noexcept; - [[nodiscard]] const variable_set& get_variables() const noexcept; + [[nodiscard]] const variable_list& get_variables() const noexcept; template < typename... Args > [[nodiscard]] uvalue create(Args&&... args) const; @@ -321,7 +321,7 @@ namespace meta_hpp [[nodiscard]] number_type get_underlying_type() const noexcept; - [[nodiscard]] const evalue_set& get_evalues() const noexcept; + [[nodiscard]] const evalue_list& get_evalues() const noexcept; [[nodiscard]] evalue get_evalue(std::string_view name) const noexcept; @@ -471,15 +471,15 @@ namespace meta_hpp::detail const std::size_t align; const any_type_list argument_types; - class_set base_classes; - class_set derived_classes; - constructor_set constructors; - destructor_set destructors; - function_set functions; - member_set members; - method_set methods; + class_list base_classes; + class_list derived_classes; + constructor_list constructors; + destructor_list destructors; + function_list functions; + member_list members; + method_list methods; typedef_map typedefs; - variable_set variables; + variable_list variables; struct upcast_func_t final { using upcast_t = void* (*)(void*); @@ -498,13 +498,14 @@ namespace meta_hpp::detail struct upcast_func_list_t final { using upcasts_t = std::vector; + using vbases_t = std::set>; upcasts_t upcasts{}; - class_set vbases{}; + vbases_t vbases{}; bool is_ambiguous{}; upcast_func_list_t(const upcast_func_t& _upcast); - upcast_func_list_t(upcasts_t _upcasts, class_set _vbases); + upcast_func_list_t(upcasts_t _upcasts, vbases_t _vbases); [[nodiscard]] void* apply(void* ptr) const noexcept; [[nodiscard]] const void* apply(const void* ptr) const noexcept; @@ -543,7 +544,7 @@ namespace meta_hpp::detail const enum_bitflags flags; const number_type underlying_type; - evalue_set evalues; + evalue_list evalues; template < enum_kind Enum > explicit enum_type_data(type_list); diff --git a/headers/meta.hpp/meta_types/class_type.hpp b/headers/meta.hpp/meta_types/class_type.hpp index 8af5234..e1fd283 100644 --- a/headers/meta.hpp/meta_types/class_type.hpp +++ b/headers/meta.hpp/meta_types/class_type.hpp @@ -59,7 +59,7 @@ namespace meta_hpp::detail } } - inline class_type_data::upcast_func_list_t::upcast_func_list_t(upcasts_t _upcasts, class_set _vbases) + inline class_type_data::upcast_func_list_t::upcast_func_list_t(upcasts_t _upcasts, vbases_t _vbases) : upcasts{std::move(_upcasts)} , vbases{std::move(_vbases)} {} @@ -84,7 +84,7 @@ namespace meta_hpp::detail new_upcasts.insert(new_upcasts.end(), l.upcasts.begin(), l.upcasts.end()); new_upcasts.insert(new_upcasts.end(), r.upcasts.begin(), r.upcasts.end()); - class_set new_vbases; + class_type_data::upcast_func_list_t::vbases_t new_vbases; new_vbases.insert(l.vbases.begin(), l.vbases.end()); new_vbases.insert(r.vbases.begin(), r.vbases.end()); @@ -118,31 +118,31 @@ namespace meta_hpp return data_->argument_types; } - inline const class_set& class_type::get_base_classes() const noexcept { + inline const class_list& class_type::get_base_classes() const noexcept { return data_->base_classes; } - inline const class_set& class_type::get_derived_classes() const noexcept { + inline const class_list& class_type::get_derived_classes() const noexcept { return data_->derived_classes; } - inline const constructor_set& class_type::get_constructors() const noexcept { + inline const constructor_list& class_type::get_constructors() const noexcept { return data_->constructors; } - inline const destructor_set& class_type::get_destructors() const noexcept { + inline const destructor_list& class_type::get_destructors() const noexcept { return data_->destructors; } - inline const function_set& class_type::get_functions() const noexcept { + inline const function_list& class_type::get_functions() const noexcept { return data_->functions; } - inline const member_set& class_type::get_members() const noexcept { + inline const member_list& class_type::get_members() const noexcept { return data_->members; } - inline const method_set& class_type::get_methods() const noexcept { + inline const method_list& class_type::get_methods() const noexcept { return data_->methods; } @@ -150,7 +150,7 @@ namespace meta_hpp return data_->typedefs; } - inline const variable_set& class_type::get_variables() const noexcept { + inline const variable_list& class_type::get_variables() const noexcept { return data_->variables; } @@ -266,8 +266,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const function& function = base.get_function(name, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const function& function = iter->get_function(name, recursively) ) { return function; } } @@ -284,8 +284,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const member& member = base.get_member(name, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const member& member = iter->get_member(name, recursively) ) { return member; } } @@ -302,8 +302,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const method& method = base.get_method(name, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const method& method = iter->get_method(name, recursively) ) { return method; } } @@ -318,8 +318,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const any_type& type = base.get_typedef(name, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const any_type& type = iter->get_typedef(name, recursively) ) { return type; } } @@ -336,8 +336,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const variable& variable = base.get_variable(name, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const variable& variable = iter->get_variable(name, recursively) ) { return variable; } } @@ -418,8 +418,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const function& function = base.get_function_with(name, first, last, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const function& function = iter->get_function_with(name, first, last, recursively) ) { return function; } } @@ -476,8 +476,8 @@ namespace meta_hpp } if ( recursively ) { - for ( const class_type& base : data_->base_classes ) { - if ( const method& method = base.get_method_with(name, first, last, recursively) ) { + for ( auto iter{data_->base_classes.rbegin()}, end{data_->base_classes.rend()}; iter != end; ++iter ) { + if ( const method& method = iter->get_method_with(name, first, last, recursively) ) { return method; } } diff --git a/headers/meta.hpp/meta_types/enum_type.hpp b/headers/meta.hpp/meta_types/enum_type.hpp index a70af67..5895b8c 100644 --- a/headers/meta.hpp/meta_types/enum_type.hpp +++ b/headers/meta.hpp/meta_types/enum_type.hpp @@ -34,7 +34,7 @@ namespace meta_hpp return data_->underlying_type; } - inline const evalue_set& enum_type::get_evalues() const noexcept { + inline const evalue_list& enum_type::get_evalues() const noexcept { return data_->evalues; }