meta: a draft version of typelist and operations for it
This commit is contained in:
parent
8fef779a91
commit
533a09625c
File diff suppressed because it is too large
Load Diff
@ -26,12 +26,36 @@ namespace test_meta {
|
|||||||
using namespace meta;
|
using namespace meta;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Test integral constant
|
* Types to behave like Fixtures
|
||||||
*/
|
*/
|
||||||
// Test type_of fixture
|
// Test type_of fixture
|
||||||
template<class T> struct TestTypeOf {
|
template<class T> struct TestTypeOf {
|
||||||
using type = T;
|
using type = T;
|
||||||
};
|
};
|
||||||
|
template<class T1, class T2> struct MfunBin {
|
||||||
|
using type = int;
|
||||||
|
};
|
||||||
|
template<int a, int b> struct MfunBin_i {
|
||||||
|
using type = int;
|
||||||
|
};
|
||||||
|
template<class T1> struct MfunUn1 {
|
||||||
|
using type = int;
|
||||||
|
};
|
||||||
|
template<class T1> struct MfunUn2 {
|
||||||
|
using type = int;
|
||||||
|
};
|
||||||
|
|
||||||
|
template <typename T> struct Pred_isInt {
|
||||||
|
using type = std::is_integral<T>;
|
||||||
|
};
|
||||||
|
|
||||||
|
template <typename T> struct Pred_isVoid {
|
||||||
|
using type = std::is_void<T>;
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Test integral constant
|
||||||
|
*/
|
||||||
TEST(Tmeta_integral, Integreal_type_) {
|
TEST(Tmeta_integral, Integreal_type_) {
|
||||||
EXPECT_EQ(true, (std::is_same<int, type_<TestTypeOf<int>>>::value));
|
EXPECT_EQ(true, (std::is_same<int, type_<TestTypeOf<int>>>::value));
|
||||||
}
|
}
|
||||||
@ -146,16 +170,102 @@ namespace test_meta {
|
|||||||
/*
|
/*
|
||||||
* Test invoke
|
* Test invoke
|
||||||
*/
|
*/
|
||||||
template<class T1, class T2> struct MetaFunction { using type = int; };
|
|
||||||
template<typename... Args> struct MetaClass {using apply = int; };
|
|
||||||
TEST(Tmeta_invoke, Invoke) {
|
TEST(Tmeta_invoke, Invoke) {
|
||||||
//EXPECT_EQ (true, (is_evaluable<MetaFunction, int .long>()));
|
using Q = quote<MfunBin>;
|
||||||
|
using Qi = quote_i<int, MfunBin_i>;
|
||||||
|
using Q1 = quote<MfunUn1>;
|
||||||
|
using Q2 = quote<MfunUn2>;
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<int, identity_t<int>>()));
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (is_applicable_t<MfunBin, int, long>()));
|
||||||
|
EXPECT_EQ (false, (is_applicable_t<MfunBin, int>()));
|
||||||
|
EXPECT_EQ (true, (is_applicable_qt<Q, int, long>()));
|
||||||
|
EXPECT_EQ (false, (is_applicable_qt<Q, int>()));
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (is_applicable_it<int, MfunBin_i, 7, 42>()));
|
||||||
|
EXPECT_EQ (false, (is_applicable_it<int, MfunBin_i, 42>()));
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<defer<MfunBin, int, void>::type, MfunBin<int, void>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<defer<MfunBin, void>::type, nil_>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<defer_i<int, MfunBin_i, 7, 42>::type, MfunBin_i<7, 42>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<defer_i<int, MfunBin_i, 7>::type, nil_>()));
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<invoke<Q, int>, nil_>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<invoke<Q, int, void*>, MfunBin<int, void*>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<invoke<Qi, int_<7>, int_<42>>, MfunBin_i<7, 42>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<invoke<Qi, int_<42>>, nil_>()));
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<invoke<compose<Q1, Q2>, int>, MfunUn1<MfunUn2<int>>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<
|
||||||
|
invoke<compose<Q1, Q2, Qi>, int_<7>, int_<42>>,
|
||||||
|
MfunUn1<MfunUn2<MfunBin_i<7, 42>>>
|
||||||
|
>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<
|
||||||
|
invoke<compose<Q1, Q2, Qi>, int_<42>>,
|
||||||
|
MfunUn1<MfunUn2<nil_>>
|
||||||
|
>()));
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<invoke<bind_front<Q, int>, long>, MfunBin<int, long>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<invoke<bind_back<Q, int>, long>, MfunBin<long, int>>()));
|
||||||
|
|
||||||
}
|
}
|
||||||
/*
|
/*
|
||||||
* Test typelist
|
* Test typelist
|
||||||
*/
|
*/
|
||||||
template<class T1, class T2> struct F {};
|
TEST(Tmeta_typelist, Basics) {
|
||||||
TEST(Tmeta_typelist, List_fold) {
|
using l1 = typelist<int, int, int>;
|
||||||
|
using l2 = typelist<int, void*, int, void*>;
|
||||||
|
using l3 = typelist<>;
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<l1, typelist<int>::times<3>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<l2, typelist<int, void*>::times<2>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<l3, typelist<>::times<3>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<l3, typelist<int>::times<0>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<typelist<short, double>, pair<short, double>>()));
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<l1, repeat <int_<3>, int>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<l2, repeat_c <2, int, void*>>()));
|
||||||
|
|
||||||
|
|
||||||
|
EXPECT_EQ (3, size<l1>());
|
||||||
|
EXPECT_EQ (true, empty<l3>());
|
||||||
|
|
||||||
|
// pass typelist to an invocable
|
||||||
|
EXPECT_EQ (true, (std::is_same<type_<
|
||||||
|
apply<quote<MfunBin>, typelist<int, long>>
|
||||||
|
>,
|
||||||
|
MfunBin<int, long>
|
||||||
|
>()));
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST(Tmeta_typelist, Element_access) {
|
||||||
|
using l = typelist<char, void, long, double, short>;
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<char, at_c<l, 0>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<long, at_c<l, 2>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<nil_, at_c<l, 5>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<void, at<l, int_<1>>>()));
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<char, front<l>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<short, back<l>>()));
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST(Tmeta_typelist, Concat) {
|
||||||
|
using l1 = typelist<int, long, void>;
|
||||||
|
using l2 = typelist<void*, int*>;
|
||||||
|
using l3 = typelist<double, long double, short>;
|
||||||
|
using l4 = typelist<>;
|
||||||
|
using conc = typelist<int, long, void, void*, int*, double, long double, short>;
|
||||||
|
|
||||||
|
EXPECT_EQ(true, (std::is_same<l4, cat<l4, l4>>()));
|
||||||
|
EXPECT_EQ(true, (std::is_same<conc, cat<l1, l2, l3, l4>>()));
|
||||||
|
EXPECT_EQ(true, (std::is_same<conc, cat<l1, l4, l2, l3>>()));
|
||||||
|
EXPECT_EQ(true, (std::is_same<conc, cat<l4, l1, l2, l3>>()));
|
||||||
|
}
|
||||||
|
|
||||||
|
template<class T1, class T2> struct F {}; // binary invocable
|
||||||
|
TEST(Tmeta_typelist, Fold) {
|
||||||
struct X1 {};
|
struct X1 {};
|
||||||
struct X2 {};
|
struct X2 {};
|
||||||
struct X3 {};
|
struct X3 {};
|
||||||
@ -168,29 +278,116 @@ namespace test_meta {
|
|||||||
EXPECT_EQ(true, (std::is_same<fold<typelist<X1, X2, X3>, void, Q>, F<F<F<void, X1>, X2>, X3>>()));
|
EXPECT_EQ(true, (std::is_same<fold<typelist<X1, X2, X3>, void, Q>, F<F<F<void, X1>, X2>, X3>>()));
|
||||||
EXPECT_EQ(true, (std::is_same<fold<typelist<X1, X2, X3, X4>, void, Q>, F<F<F<F<void, X1>, X2>, X3>, X4>>()));
|
EXPECT_EQ(true, (std::is_same<fold<typelist<X1, X2, X3, X4>, void, Q>, F<F<F<F<void, X1>, X2>, X3>, X4>>()));
|
||||||
|
|
||||||
//EXPECT_EQ(true, (std::is_same<rev_fold<typelist<>, void, Q>, void>()));
|
EXPECT_EQ(true, (std::is_same<rev_fold<typelist<>, void, Q>, void>()));
|
||||||
EXPECT_EQ(true, (std::is_same<rev_fold<typelist<X1>, void, Q>, F<X1, void>>()));
|
EXPECT_EQ(true, (std::is_same<rev_fold<typelist<X1>, void, Q>, F<X1, void>>()));
|
||||||
EXPECT_EQ(true, (std::is_same<rev_fold<typelist<X1, X2>, void, Q>, F<X1, F<X2, void>>>()));
|
EXPECT_EQ(true, (std::is_same<rev_fold<typelist<X1, X2>, void, Q>, F<X1, F<X2, void>>>()));
|
||||||
EXPECT_EQ(true, (std::is_same<rev_fold<typelist<X1, X2, X3>, void, Q>, F<X1, F<X2, F<X3, void>>>>()));
|
EXPECT_EQ(true, (std::is_same<rev_fold<typelist<X1, X2, X3>, void, Q>, F<X1, F<X2, F<X3, void>>>>()));
|
||||||
EXPECT_EQ(true, (std::is_same<rev_fold<typelist<X1, X2, X3, X4>, void, Q>, F<X1, F<X2, F<X3, F<X4, void>>>>>()));
|
EXPECT_EQ(true, (std::is_same<rev_fold<typelist<X1, X2, X3, X4>, void, Q>, F<X1, F<X2, F<X3, F<X4, void>>>>>()));
|
||||||
}
|
}
|
||||||
TEST(Tmeta_typelist, ListOperations) {
|
|
||||||
using l1 = typelist<int, short, long>;
|
|
||||||
using l2 = typelist<>;
|
|
||||||
using l3 = typelist<float, double, long double>;
|
|
||||||
using l4 = typelist<void*, char*>;
|
|
||||||
using conc = typelist<int, short, long, float, double, long double, void*, char*>;
|
|
||||||
using rep = typelist<int, int, int>;
|
|
||||||
|
|
||||||
EXPECT_EQ(3, size<l1>());
|
TEST(Tmeta_typelist, PushPopReverse) {
|
||||||
EXPECT_EQ(true, empty<l2>());
|
using list = typelist <int, long, void>;
|
||||||
|
using l_char = typelist <int, long, void, char>;
|
||||||
|
using l_cc = typelist <int, long, void, char, char>;
|
||||||
|
using char_l = typelist <char, int, long, void>;
|
||||||
|
using cc_l = typelist<char, char, int, long, void>;
|
||||||
|
using rev = typelist<void, long, int>;
|
||||||
|
|
||||||
EXPECT_EQ(true, (std::is_same<conc, concat<l1, l2, l3, l4>>()));
|
EXPECT_EQ (true, (std::is_same<char_l, push_front<list, char>>()));
|
||||||
EXPECT_EQ(true, (std::is_same<rep, repeat_n<int_<3>, int>>()));
|
EXPECT_EQ (true, (std::is_same<cc_l, push_front<list, char, char>>()));
|
||||||
EXPECT_EQ(true, (std::is_same<int, front<l1>>()));
|
EXPECT_EQ (true, (std::is_same<list, pop_front <char_l>>()));
|
||||||
EXPECT_EQ(true, (std::is_same<long, back<l1>>()));
|
EXPECT_EQ (true, (std::is_same<l_char, push_back <list, char>>()));
|
||||||
EXPECT_EQ(true, (std::is_same<double, at<l3, int_<1>>>()));
|
EXPECT_EQ (true, (std::is_same<l_cc, push_back <list, char, char>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<list, pop_back <l_char>>()));
|
||||||
|
|
||||||
EXPECT_EQ(true, (std::is_same<typelist<short, long>, pop_front<l1>>()));
|
EXPECT_EQ (true, (std::is_same<rev, reverse <list>>()));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TEST(Tmeta_typelist, Transform) {
|
||||||
|
using QBin = quote<MfunBin>;
|
||||||
|
using QUn = quote<MfunUn1>;
|
||||||
|
|
||||||
|
using l1 = typelist<char, int, float>;
|
||||||
|
using l2 = typelist<void, void, void>;
|
||||||
|
using r = typelist<int, int, int>;
|
||||||
|
using r_ulazy = typelist <MfunUn1<char>, MfunUn1<int>, MfunUn1<float>>;
|
||||||
|
using r_blazy = typelist <MfunBin<char, void>, MfunBin<int, void>, MfunBin<float, void>>;
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<r, transform<l1, QUn>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<r, transform<l1, l2, QBin>>()));
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<r_ulazy, transform_lazy<l1, QUn>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<r_blazy, transform_lazy<l1, l2, QBin>>()));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
TEST(Tmeta_typelist, Find) {
|
||||||
|
using l1 = typelist <int, char, long, float>;
|
||||||
|
using l2 = typelist <char, long, float>;
|
||||||
|
using l3 = typelist <long, float>;
|
||||||
|
using empty = typelist<>;
|
||||||
|
|
||||||
|
EXPECT_EQ(true, (std::is_same<index_t_<1>, find_if<l1, same_as<char>>>()));
|
||||||
|
EXPECT_EQ(true, (std::is_same<Npos, find_if<empty, same_as<char>>>()));
|
||||||
|
EXPECT_EQ(true, (std::is_same<Npos, find_if<l1, same_as<double>>>()));
|
||||||
|
|
||||||
|
EXPECT_EQ(true, (std::is_same<index_t_<2>, find<l1, long>>()));
|
||||||
|
|
||||||
|
EXPECT_EQ(true, (std::is_same<l2, seek_if<l1, same_as<char>>>()));
|
||||||
|
EXPECT_EQ(true, (std::is_same<empty, seek_if<empty, same_as<char>>>()));
|
||||||
|
EXPECT_EQ(true, (std::is_same<empty, seek_if<l1, same_as<double>>>()));
|
||||||
|
|
||||||
|
EXPECT_EQ(true, (std::is_same<l3, seek<l1, long>>()));
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST(Tmeta_typelist, Count) {
|
||||||
|
using list = typelist<int, void*, char, int, long*, char, int, short>;
|
||||||
|
using empty = typelist<>;
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<size_t_<3>, count_if<list, same_as<int>>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<size_t_<2>, count_if<list, same_as<char>>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<size_t_<0>, count_if<list, same_as<double>>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<size_t_<0>, count_if<empty, int>>()));
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<size_t_<1>, count<list, void*>>()));
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST(Tmeta_typelist, Filter) {
|
||||||
|
using Q1 = quote<Pred_isInt>;
|
||||||
|
using Q2 = quote<Pred_isVoid>;
|
||||||
|
using list = typelist<int, float, char, long*, short, double, void*>;
|
||||||
|
using filtered = typelist<int, char, short>;
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<filtered, filter<list, Q1>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<typelist<>, filter<typelist<>, Q1>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<typelist<>, filter<list, Q2>>()));
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST(Tmeta_typelist, Replace) {
|
||||||
|
using Q = quote<Pred_isInt>;
|
||||||
|
using list = typelist<int, float, char, long*, short, double, void*>;
|
||||||
|
using res = typelist<void,float, void, long*, void, double, void*>;
|
||||||
|
using repl = typelist<int, float, void, long*, short, double, void*>;
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<res, replace_if<list, Q, void>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<typelist<>, replace_if<typelist<>, Q, void>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<res, replace_if<res, Q, void>>()));
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<repl, replace<list, char, void>>()));
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST (Tmeta_typelist, AllAnyNone) {
|
||||||
|
using l1 = typelist<int, float, char, long*, short, double, void*>;
|
||||||
|
using l2 = typelist<int, char, long, short>;
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<false_, all_of<l1, quote<Pred_isInt>>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<true_, all_of<l2, quote<Pred_isInt>>>()));
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<true_, any_of<l1, quote<Pred_isInt>>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<false_, any_of<l2, quote<Pred_isVoid>>>()));
|
||||||
|
|
||||||
|
EXPECT_EQ (true, (std::is_same<true_, none_of<l1, quote<Pred_isVoid>>>()));
|
||||||
|
EXPECT_EQ (true, (std::is_same<false_, none_of<l1, quote<Pred_isInt>>>()));
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user