mirror of
https://github.com/BlackMATov/meta.hpp.git
synced 2025-12-15 03:45:30 +07:00
delete default value ctor
This commit is contained in:
@@ -28,7 +28,7 @@ namespace meta_hpp::function_detail
|
||||
: function_traits<R(*)(Args...)> {};
|
||||
|
||||
template < auto Function, std::size_t... Is >
|
||||
value invoke(value* args, std::index_sequence<Is...>) {
|
||||
std::optional<value> invoke(value* args, std::index_sequence<Is...>) {
|
||||
using ft = function_traits<decltype(Function)>;
|
||||
using return_type = typename ft::return_type;
|
||||
using argument_types = typename ft::argument_types;
|
||||
@@ -43,7 +43,7 @@ namespace meta_hpp::function_detail
|
||||
if constexpr ( std::is_void_v<return_type> ) {
|
||||
std::invoke(Function,
|
||||
*std::get<Is>(typed_arguments)...);
|
||||
return value{};
|
||||
return std::nullopt;
|
||||
} else {
|
||||
return_type return_value = std::invoke(Function,
|
||||
*std::get<Is>(typed_arguments)...);
|
||||
@@ -52,7 +52,7 @@ namespace meta_hpp::function_detail
|
||||
}
|
||||
|
||||
template < auto Function >
|
||||
value invoke(value* args, std::size_t arg_count) {
|
||||
std::optional<value> invoke(value* args, std::size_t arg_count) {
|
||||
using ft = function_traits<decltype(Function)>;
|
||||
|
||||
if ( arg_count != ft::arity ) {
|
||||
@@ -84,7 +84,7 @@ namespace meta_hpp
|
||||
}
|
||||
|
||||
template < typename... Args >
|
||||
value invoke(Args&&... args) const {
|
||||
std::optional<value> invoke(Args&&... args) const {
|
||||
std::array<value, sizeof...(Args)> vargs{{std::forward<Args>(args)...}};
|
||||
return invoke_(vargs.data(), vargs.size());
|
||||
}
|
||||
@@ -118,7 +118,7 @@ namespace meta_hpp
|
||||
private:
|
||||
family_id fid_;
|
||||
std::string id_;
|
||||
value(*invoke_)(value*, std::size_t);
|
||||
std::optional<value>(*invoke_)(value*, std::size_t);
|
||||
std::map<std::string, data_info, std::less<>> datas_;
|
||||
};
|
||||
}
|
||||
|
||||
@@ -40,7 +40,7 @@ namespace meta_hpp::method_detail
|
||||
: method_traits<R(Base::*)(Args...) const> {};
|
||||
|
||||
template < auto Method, std::size_t... Is >
|
||||
value invoke([[maybe_unused]] void* instance, value* args, std::index_sequence<Is...>) {
|
||||
std::optional<value> invoke([[maybe_unused]] void* instance, value* args, std::index_sequence<Is...>) {
|
||||
using mt = method_traits<decltype(Method)>;
|
||||
using return_type = typename mt::return_type;
|
||||
using instance_type = typename mt::instance_type;
|
||||
@@ -57,7 +57,7 @@ namespace meta_hpp::method_detail
|
||||
std::invoke(Method,
|
||||
std::ref(*static_cast<instance_type*>(instance)),
|
||||
*std::get<Is>(typed_arguments)...);
|
||||
return value{};
|
||||
return std::nullopt;
|
||||
} else {
|
||||
return_type return_value = std::invoke(Method,
|
||||
std::ref(*static_cast<instance_type*>(instance)),
|
||||
@@ -67,7 +67,7 @@ namespace meta_hpp::method_detail
|
||||
}
|
||||
|
||||
template < auto Method >
|
||||
value invoke(void* instance, value* args, std::size_t arg_count) {
|
||||
std::optional<value> invoke(void* instance, value* args, std::size_t arg_count) {
|
||||
using mt = method_traits<decltype(Method)>;
|
||||
|
||||
if ( arg_count != mt::arity ) {
|
||||
@@ -78,7 +78,7 @@ namespace meta_hpp::method_detail
|
||||
}
|
||||
|
||||
template < auto Method, std::size_t... Is >
|
||||
value cinvoke([[maybe_unused]] const void* instance, value* args, std::index_sequence<Is...>) {
|
||||
std::optional<value> cinvoke([[maybe_unused]] const void* instance, value* args, std::index_sequence<Is...>) {
|
||||
using mt = method_traits<decltype(Method)>;
|
||||
using return_type = typename mt::return_type;
|
||||
using instance_type = typename mt::instance_type;
|
||||
@@ -96,7 +96,7 @@ namespace meta_hpp::method_detail
|
||||
std::invoke(Method,
|
||||
std::ref(*static_cast<const instance_type*>(instance)),
|
||||
*std::get<Is>(typed_arguments)...);
|
||||
return value{};
|
||||
return std::nullopt;
|
||||
} else {
|
||||
return_type return_value = std::invoke(Method,
|
||||
std::ref(*static_cast<const instance_type*>(instance)),
|
||||
@@ -109,7 +109,7 @@ namespace meta_hpp::method_detail
|
||||
}
|
||||
|
||||
template < auto Method >
|
||||
value cinvoke(const void* instance, value* args, std::size_t arg_count) {
|
||||
std::optional<value> cinvoke(const void* instance, value* args, std::size_t arg_count) {
|
||||
using mt = method_traits<decltype(Method)>;
|
||||
|
||||
if ( arg_count != mt::arity ) {
|
||||
@@ -141,13 +141,13 @@ namespace meta_hpp
|
||||
}
|
||||
|
||||
template < typename... Args >
|
||||
value invoke(void* instance, Args&&... args) const {
|
||||
std::optional<value> invoke(void* instance, Args&&... args) const {
|
||||
std::array<value, sizeof...(Args)> vargs{{std::forward<Args>(args)...}};
|
||||
return invoke_(instance, vargs.data(), vargs.size());
|
||||
}
|
||||
|
||||
template < typename... Args >
|
||||
value invoke(const void* instance, Args&&... args) const {
|
||||
std::optional<value> invoke(const void* instance, Args&&... args) const {
|
||||
std::array<value, sizeof...(Args)> vargs{{std::forward<Args>(args)...}};
|
||||
return cinvoke_(instance, vargs.data(), vargs.size());
|
||||
}
|
||||
@@ -182,8 +182,8 @@ namespace meta_hpp
|
||||
private:
|
||||
family_id fid_;
|
||||
std::string id_;
|
||||
value(*invoke_)(void*, value*, std::size_t);
|
||||
value(*cinvoke_)(const void*, value*, std::size_t);
|
||||
std::optional<value>(*invoke_)(void*, value*, std::size_t);
|
||||
std::optional<value>(*cinvoke_)(const void*, value*, std::size_t);
|
||||
std::map<std::string, data_info, std::less<>> datas_;
|
||||
};
|
||||
}
|
||||
|
||||
@@ -12,28 +12,60 @@ namespace meta_hpp
|
||||
{
|
||||
class value {
|
||||
public:
|
||||
value() = default;
|
||||
value() = delete;
|
||||
|
||||
value(value&&) = default;
|
||||
value(const value&) = default;
|
||||
|
||||
value& operator=(value&&) = default;
|
||||
value& operator=(const value&) = default;
|
||||
|
||||
template < typename T >
|
||||
value(T&& value)
|
||||
: raw_{std::forward<T>(value)} {}
|
||||
|
||||
template < typename T >
|
||||
value& operator=(T&& value) noexcept {
|
||||
raw_ = std::forward<T>(value);
|
||||
return *this;
|
||||
}
|
||||
|
||||
template < typename T, typename... Args >
|
||||
value(std::in_place_type_t<T>, Args&&... args)
|
||||
: raw_{std::in_place_type<T>, std::forward<Args>(args)...} {}
|
||||
|
||||
template < typename T, typename U, typename... Args >
|
||||
value(std::in_place_type_t<T>, std::initializer_list<U> ilist, Args&&... args)
|
||||
: raw_{std::in_place_type<T>, ilist, std::forward<Args>(args)...} {}
|
||||
|
||||
void swap(value& other) noexcept {
|
||||
raw_.swap(other.raw_);
|
||||
}
|
||||
|
||||
template < typename T >
|
||||
auto cast() const {
|
||||
T cast() && {
|
||||
return std::any_cast<T>(std::move(raw_));
|
||||
}
|
||||
|
||||
template < typename T >
|
||||
T cast() & {
|
||||
return std::any_cast<T>(raw_);
|
||||
}
|
||||
|
||||
template < typename T >
|
||||
auto try_cast() noexcept {
|
||||
T cast() const & {
|
||||
return std::any_cast<T>(raw_);
|
||||
}
|
||||
|
||||
template < typename T >
|
||||
std::add_pointer_t<T>
|
||||
try_cast() noexcept {
|
||||
return std::any_cast<T>(&raw_);
|
||||
}
|
||||
|
||||
template < typename T >
|
||||
auto try_cast() const noexcept {
|
||||
std::add_pointer_t<std::add_const_t<T>>
|
||||
try_cast() const noexcept {
|
||||
return std::any_cast<T>(&raw_);
|
||||
}
|
||||
public:
|
||||
@@ -60,4 +92,8 @@ namespace meta_hpp
|
||||
private:
|
||||
std::any raw_;
|
||||
};
|
||||
|
||||
inline void swap(value& l, value& r) noexcept {
|
||||
l.swap(r);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -133,18 +133,18 @@ TEST_CASE("meta/examples/simple") {
|
||||
ivec2 v2{1,2};
|
||||
CHECK(ivec2_x_info.get(&v2).cast<int>() == 1);
|
||||
CHECK(ivec2_y_info.get(&v2).cast<int>() == 2);
|
||||
CHECK(ivec2_dot_info.invoke(&v2, v2).cast<int>() == 5);
|
||||
CHECK(ivec2_length2_info.invoke(&v2).cast<int>() == 5);
|
||||
CHECK(ivec2_dot_info.invoke(&v2, v2)->cast<int>() == 5);
|
||||
CHECK(ivec2_length2_info.invoke(&v2)->cast<int>() == 5);
|
||||
}
|
||||
|
||||
{
|
||||
ivec2 v = iadd2_info.invoke(ivec2{1,2}, ivec2{3,4}).cast<ivec2>();
|
||||
ivec2 v = iadd2_info.invoke(ivec2{1,2}, ivec2{3,4})->cast<ivec2>();
|
||||
CHECK(v.x == 4);
|
||||
CHECK(v.y == 6);
|
||||
}
|
||||
|
||||
{
|
||||
ivec3 v = iadd3_info.invoke(ivec3{1,2,3}, ivec3{3,4,5}).cast<ivec3>();
|
||||
ivec3 v = iadd3_info.invoke(ivec3{1,2,3}, ivec3{3,4,5})->cast<ivec3>();
|
||||
CHECK(v.x == 4);
|
||||
CHECK(v.y == 6);
|
||||
CHECK(v.z == 8);
|
||||
|
||||
@@ -55,17 +55,17 @@ TEST_CASE("meta/function") {
|
||||
}
|
||||
|
||||
SUBCASE("int_return") {
|
||||
CHECK(int_f_void_info.invoke().cast<int>() == 1);
|
||||
CHECK(int_f_void_info.invoke()->cast<int>() == 1);
|
||||
CHECK_THROWS_AS(int_f_void_info.invoke(1), std::logic_error);
|
||||
|
||||
CHECK_THROWS_AS(int_f_int_info.invoke(), std::logic_error);
|
||||
CHECK(int_f_int_info.invoke(1).cast<int>() == 1);
|
||||
CHECK(int_f_int_info.invoke(1)->cast<int>() == 1);
|
||||
CHECK_THROWS_AS(int_f_int_info.invoke(1.f), std::logic_error);
|
||||
CHECK_THROWS_AS(int_f_int_info.invoke(1, 2), std::logic_error);
|
||||
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(), std::logic_error);
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(1), std::logic_error);
|
||||
CHECK(int_f_int2_info.invoke(1, 2).cast<int>() == 3);
|
||||
CHECK(int_f_int2_info.invoke(1, 2)->cast<int>() == 3);
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(1.f, 2), std::logic_error);
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(1, 2.f), std::logic_error);
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(1, 2, 3), std::logic_error);
|
||||
|
||||
@@ -75,17 +75,17 @@ TEST_CASE("meta/non_const_method") {
|
||||
SUBCASE("int_return") {
|
||||
clazz instance;
|
||||
|
||||
CHECK(int_f_void_info.invoke(&instance).cast<int>() == 1);
|
||||
CHECK(int_f_void_info.invoke(&instance)->cast<int>() == 1);
|
||||
CHECK_THROWS_AS(int_f_void_info.invoke(&instance, 1), std::logic_error);
|
||||
|
||||
CHECK_THROWS_AS(int_f_int_info.invoke(&instance), std::logic_error);
|
||||
CHECK(int_f_int_info.invoke(&instance, 1).cast<int>() == 1);
|
||||
CHECK(int_f_int_info.invoke(&instance, 1)->cast<int>() == 1);
|
||||
CHECK_THROWS_AS(int_f_int_info.invoke(&instance, 1.f), std::logic_error);
|
||||
CHECK_THROWS_AS(int_f_int_info.invoke(&instance, 1, 2), std::logic_error);
|
||||
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(&instance), std::logic_error);
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(&instance, 1), std::logic_error);
|
||||
CHECK(int_f_int2_info.invoke(&instance, 1, 2).cast<int>() == 3);
|
||||
CHECK(int_f_int2_info.invoke(&instance, 1, 2)->cast<int>() == 3);
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(&instance, 1.f, 2), std::logic_error);
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(&instance, 1, 2.f), std::logic_error);
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(&instance, 1, 2, 3), std::logic_error);
|
||||
@@ -143,24 +143,24 @@ TEST_CASE("meta/const_method") {
|
||||
SUBCASE("int_return") {
|
||||
clazz instance;
|
||||
|
||||
CHECK(int_f_void_info.invoke(&instance).cast<int>() == 1);
|
||||
CHECK(int_f_void_info.invoke(&instance)->cast<int>() == 1);
|
||||
CHECK_THROWS_AS(int_f_void_info.invoke(&instance, 1), std::logic_error);
|
||||
|
||||
CHECK_THROWS_AS(int_f_int_info.invoke(&instance), std::logic_error);
|
||||
CHECK(int_f_int_info.invoke(&instance, 1).cast<int>() == 1);
|
||||
CHECK(int_f_int_info.invoke(&instance, 1)->cast<int>() == 1);
|
||||
CHECK_THROWS_AS(int_f_int_info.invoke(&instance, 1.f), std::logic_error);
|
||||
CHECK_THROWS_AS(int_f_int_info.invoke(&instance, 1, 2), std::logic_error);
|
||||
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(&instance), std::logic_error);
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(&instance, 1), std::logic_error);
|
||||
CHECK(int_f_int2_info.invoke(&instance, 1, 2).cast<int>() == 3);
|
||||
CHECK(int_f_int2_info.invoke(&instance, 1, 2)->cast<int>() == 3);
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(&instance, 1.f, 2), std::logic_error);
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(&instance, 1, 2.f), std::logic_error);
|
||||
CHECK_THROWS_AS(int_f_int2_info.invoke(&instance, 1, 2, 3), std::logic_error);
|
||||
|
||||
const clazz& cinstance = instance;
|
||||
CHECK(int_f_void_info.invoke(&cinstance).cast<int>() == 1);
|
||||
CHECK(int_f_int_info.invoke(&cinstance, 1).cast<int>() == 1);
|
||||
CHECK(int_f_int2_info.invoke(&cinstance, 1, 2).cast<int>() == 3);
|
||||
CHECK(int_f_void_info.invoke(&cinstance)->cast<int>() == 1);
|
||||
CHECK(int_f_int_info.invoke(&cinstance, 1)->cast<int>() == 1);
|
||||
CHECK(int_f_int2_info.invoke(&cinstance, 1, 2)->cast<int>() == 3);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user