@@ -0,0 +1,48 @@ | |||
/*! | |||
* \file bool.h | |||
* \brief Template meta-programming bool integral constant | |||
* | |||
* Copyright (C) 2018 Christos Choutouridis | |||
* | |||
* This program is free software: you can redistribute it and/or modify | |||
* it under the terms of the GNU Lesser General Public License as | |||
* published by the Free Software Foundation, either version 3 | |||
* of the License, or (at your option) any later version. | |||
* | |||
* This program is distributed in the hope that it will be useful, | |||
* but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
* GNU Lesser General Public License for more details. | |||
* | |||
* You should have received a copy of the GNU Lesser General Public License | |||
* along with this program. If not, see <http://www.gnu.org/licenses/>. | |||
*/ | |||
#ifndef __utl_meta_bool_h__ | |||
#define __utl_meta_bool_h__ | |||
#include <utl/impl/version.h> | |||
#include <utl/meta/integral.h> | |||
/*! | |||
* \ingroup meta | |||
* \defgroup bool | |||
* boolean constant type support header | |||
*/ | |||
//! @{ | |||
namespace utl { | |||
//! bool_ type | |||
template<bool _v> | |||
using bool_ = integral_<bool, _v>; | |||
//! The type used as a compile-time boolean with true value. | |||
typedef bool_<true> true_; | |||
//! The type used as a compile-time boolean with false value. | |||
typedef bool_<false> false_; | |||
} | |||
//! @} | |||
#endif /* __utl_meta_bool_h__ */ |
@@ -0,0 +1,64 @@ | |||
/*! | |||
* \file if.h | |||
* \brief Template meta-programming conditional helpers | |||
* | |||
* Copyright (C) 2018 Christos Choutouridis | |||
* | |||
* This program is free software: you can redistribute it and/or modify | |||
* it under the terms of the GNU Lesser General Public License as | |||
* published by the Free Software Foundation, either version 3 | |||
* of the License, or (at your option) any later version. | |||
* | |||
* This program is distributed in the hope that it will be useful, | |||
* but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
* GNU Lesser General Public License for more details. | |||
* | |||
* You should have received a copy of the GNU Lesser General Public License | |||
* along with this program. If not, see <http://www.gnu.org/licenses/>. | |||
*/ | |||
#ifndef __utl_meta_if_h__ | |||
#define __utl_meta_if_h__ | |||
#include <utl/impl/version.h> | |||
/*! | |||
* \ingroup meta | |||
* \defgroup if | |||
* conditional type support header | |||
*/ | |||
//! @{ | |||
namespace utl { | |||
//! if_ | |||
//! @{ | |||
template <bool _C, typename _T1, typename _T2> | |||
struct if_ { | |||
typedef _T1 type; | |||
}; | |||
template <typename _T1, typename _T2> | |||
struct if_ <false, _T1, _T2> { | |||
typedef _T2 type; | |||
}; | |||
//! @} | |||
//! enable_if | |||
//! @{ | |||
template <bool, typename _Tp = void> | |||
struct enable_if { }; | |||
// Partial specialization for true. | |||
template<typename _Tp> | |||
struct enable_if <true, _Tp> { | |||
typedef _Tp type; | |||
}; | |||
//! Alias template for enable_if | |||
template<bool _C, typename _Tp = void> | |||
using enable_if_t = typename enable_if<_C, _Tp>::type; | |||
//! @} | |||
} | |||
//! @} | |||
#endif /* __utl_meta_if_h__ */ |
@@ -0,0 +1,54 @@ | |||
/*! | |||
* \file integral.h | |||
* \brief Template meta-programming integral constant | |||
* | |||
* Copyright (C) 2018 Christos Choutouridis | |||
* | |||
* This program is free software: you can redistribute it and/or modify | |||
* it under the terms of the GNU Lesser General Public License as | |||
* published by the Free Software Foundation, either version 3 | |||
* of the License, or (at your option) any later version. | |||
* | |||
* This program is distributed in the hope that it will be useful, | |||
* but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
* GNU Lesser General Public License for more details. | |||
* | |||
* You should have received a copy of the GNU Lesser General Public License | |||
* along with this program. If not, see <http://www.gnu.org/licenses/>. | |||
*/ | |||
#ifndef __utl_meta_integral_h__ | |||
#define __utl_meta_integral_h__ | |||
#include <utl/impl/version.h> | |||
/*! | |||
* \ingroup meta | |||
* \defgroup integral | |||
* integral constand support header | |||
*/ | |||
//! @{ | |||
namespace utl { | |||
//! integral_constant | |||
template <typename _Tp, _Tp _v> | |||
struct integral_ { | |||
using value_type = _Tp; | |||
using type = integral_<_Tp, _v>; | |||
constexpr operator value_type() const { | |||
return value; | |||
} | |||
constexpr value_type operator()() const { | |||
return value; | |||
} | |||
static constexpr _Tp value = _v; | |||
}; | |||
template<typename _Tp, _Tp _v> | |||
constexpr _Tp integral_<_Tp, _v>::value; | |||
} | |||
//!@} | |||
#endif /* __utl_meta_integral_h__ */ |
@@ -0,0 +1,100 @@ | |||
/*! | |||
* \file logical.h | |||
* \brief Template meta-programming logic operator and type relations. | |||
* | |||
* Copyright (C) 2018 Christos Choutouridis | |||
* | |||
* This program is free software: you can redistribute it and/or modify | |||
* it under the terms of the GNU Lesser General Public License as | |||
* published by the Free Software Foundation, either version 3 | |||
* of the License, or (at your option) any later version. | |||
* | |||
* This program is distributed in the hope that it will be useful, | |||
* but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
* GNU Lesser General Public License for more details. | |||
* | |||
* You should have received a copy of the GNU Lesser General Public License | |||
* along with this program. If not, see <http://www.gnu.org/licenses/>. | |||
*/ | |||
#ifndef __utl_meta_logical_h__ | |||
#define __utl_meta_logical_h__ | |||
#include <utl/impl/version.h> | |||
#include <utl/meta/bool.h> | |||
#include <utl/meta/if.h> | |||
/*! | |||
* \ingroup meta | |||
* \defgroup logic | |||
* logic operator and type relations support header | |||
*/ | |||
//! @{ | |||
namespace utl { | |||
//! NOT implementation | |||
template<bool C_> | |||
struct not_ : bool_<!C_> { }; | |||
//! OR implementation | |||
//! @{ | |||
template<typename...> struct or_; | |||
template<> | |||
struct or_<> | |||
: false_ { }; | |||
template<typename _T1> | |||
struct or_<_T1> | |||
: _T1 { }; | |||
template<typename _T1, typename _T2> | |||
struct or_ <_T1, _T2> | |||
: if_<_T1::value, _T1, _T2>::type { }; | |||
template<typename _T1, typename _T2, typename _T3, typename... _Tn> | |||
struct or_<_T1, _T2, _T3, _Tn...> | |||
: if_<_T1::value, _T1, or_<_T2, _T3, _Tn...>>::type { }; | |||
//! @} | |||
//! AND implementation | |||
//! @{ | |||
template<typename...> struct and_; | |||
template<> | |||
struct and_<> | |||
: true_ { }; | |||
template<typename _T1> | |||
struct and_ <_T1> | |||
: _T1 { }; | |||
template<typename _T1, typename _T2> | |||
struct and_<_T1, _T2> | |||
: if_<_T1::value, _T2, _T1>::type { }; | |||
template<typename _T1, typename _T2, typename _T3, typename... _Tn> | |||
struct and_<_T1, _T2, _T3, _Tn...> | |||
: if_<_T1::value, and_<_T2, _T3, _Tn...>, _T1>::type { }; | |||
//! @} | |||
//! same | |||
//! @{ | |||
template<typename _T1, typename _T2> | |||
struct same_ : false_ { }; | |||
template<typename _Tp> | |||
struct same_ <_Tp, _Tp> : true_ { }; | |||
//! @} | |||
//! not same | |||
//! @{ | |||
template<typename _T1, typename _T2> | |||
struct not_same_ : true_ { }; | |||
template<typename _Tp> | |||
struct not_same_ <_Tp, _Tp> : false_ { }; | |||
//! @} | |||
} | |||
#endif /* __utl_meta_logical_h__ */ |
@@ -0,0 +1,64 @@ | |||
/*! | |||
* \file use.h | |||
* \brief Template meta-programming SFINAE helpers | |||
* | |||
* Copyright (C) 2018 Christos Choutouridis | |||
* | |||
* This program is free software: you can redistribute it and/or modify | |||
* it under the terms of the GNU Lesser General Public License as | |||
* published by the Free Software Foundation, either version 3 | |||
* of the License, or (at your option) any later version. | |||
* | |||
* This program is distributed in the hope that it will be useful, | |||
* but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
* GNU Lesser General Public License for more details. | |||
* | |||
* You should have received a copy of the GNU Lesser General Public License | |||
* along with this program. If not, see <http://www.gnu.org/licenses/>. | |||
*/ | |||
#ifndef __utl_meta_use_h__ | |||
#define __utl_meta_use_h__ | |||
#include <utl/impl/version.h> | |||
#include <utl/meta/logical.h> | |||
/*! | |||
* \ingroup meta | |||
* \defgroup use | |||
* conditional use support header. This is a SFINAE helper | |||
*/ | |||
//! @{ | |||
namespace utl { | |||
//! If same type resolves to _Ret, else to SFINAE | |||
//! @{ | |||
template <typename _Tp1, typename _Tp2, typename _Ret> | |||
struct use_if_same_ { | |||
using type = enable_if_t < | |||
same_<_Tp1, _Tp2>::value, | |||
_Ret | |||
>; | |||
}; | |||
template <typename _Tp1, typename _Tp2, typename _Ret> | |||
using use_if_same_t = typename use_if_same_<_Tp1, _Tp2, _Ret>::type; | |||
//! @} | |||
//! If same type resolves to SFINAE, else to _Ret | |||
//! @{ | |||
template <typename _Tp1, typename _Tp2, typename _Ret> | |||
struct discard_if_same_ { | |||
using type = enable_if_t < | |||
!same_<_Tp1, _Tp2>::value, | |||
_Ret | |||
>; | |||
}; | |||
template <typename _Tp1, typename _Tp2, typename _Ret> | |||
using discard_if_same_t = typename discard_if_same_<_Tp1, _Tp2, _Ret>::type; | |||
//! @} | |||
} | |||
//! @} | |||
#endif /* __utl_meta_use_h__ */ |
@@ -0,0 +1,63 @@ | |||
/*! | |||
* \file void.h | |||
* \brief Template meta-programming void helpers | |||
* | |||
* Copyright (C) 2018 Christos Choutouridis | |||
* | |||
* This program is free software: you can redistribute it and/or modify | |||
* it under the terms of the GNU Lesser General Public License as | |||
* published by the Free Software Foundation, either version 3 | |||
* of the License, or (at your option) any later version. | |||
* | |||
* This program is distributed in the hope that it will be useful, | |||
* but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
* GNU Lesser General Public License for more details. | |||
* | |||
* You should have received a copy of the GNU Lesser General Public License | |||
* along with this program. If not, see <http://www.gnu.org/licenses/>. | |||
*/ | |||
#ifndef __utl_meta_void_h__ | |||
#define __utl_meta_void_h__ | |||
#include <utl/impl/version.h> | |||
#include <utl/meta/bool.h> | |||
/*! \ingroup meta | |||
* \defgroup void | |||
* void_ support header | |||
*/ | |||
//! @{ | |||
namespace utl { | |||
/*! | |||
* Like boost::mpl we made void_ a complete type to allow it to be | |||
* instantiated so that it can be passed in as an object that can be | |||
* used to select an overloaded function. | |||
*/ | |||
struct void_ { | |||
typedef void_ type; | |||
}; | |||
template<typename _Tp> | |||
struct is_void_ | |||
: false_ { }; | |||
template<> | |||
struct is_void_ <void_> | |||
: true_ { }; | |||
template<typename _Tp> | |||
struct is_not_void_ | |||
: true_ { }; | |||
template<> | |||
struct is_not_void_<void_> | |||
: false_ { }; | |||
} | |||
//!@} | |||
#endif /* __utl_meta_void_h__ */ |
@@ -0,0 +1,52 @@ | |||
/*! | |||
* \file void_t.h | |||
* \brief Template meta-programming helpers | |||
* | |||
* Copyright (C) 2018 Christos Choutouridis | |||
* | |||
* This program is free software: you can redistribute it and/or modify | |||
* it under the terms of the GNU Lesser General Public License as | |||
* published by the Free Software Foundation, either version 3 | |||
* of the License, or (at your option) any later version. | |||
* | |||
* This program is distributed in the hope that it will be useful, | |||
* but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
* GNU Lesser General Public License for more details. | |||
* | |||
* You should have received a copy of the GNU Lesser General Public License | |||
* along with this program. If not, see <http://www.gnu.org/licenses/>. | |||
*/ | |||
#ifndef __utl_meta_void_t_h__ | |||
#define __utl_meta_void_t_h__ | |||
#include <utl/impl/version.h> | |||
//! \ingroup meta | |||
//! \defgroup void_t | |||
//! A void_t implementation for utl | |||
//! @{ | |||
namespace utl { | |||
/*! | |||
* Utility meta-function that maps a sequence of any types to the type void | |||
* \note The idea is: | |||
* template <typename ...> | |||
* using void_t = void; | |||
* | |||
* Until CWG 1558 (a C++14 defect), unused parameters in alias templates were not | |||
* guaranteed to ensure SFINAE and could be ignored, so earlier compilers require | |||
* a more complex definition of void_t, such as the following implementation | |||
* https://en.cppreference.com | |||
*/ | |||
template<typename... _Ts> | |||
struct void_impl { | |||
typedef void type; | |||
}; | |||
//! The actual void_t type alias | |||
template<typename... _Ts> | |||
using void_t = typename void_impl<_Ts...>::type; | |||
} | |||
//! @} | |||
#endif /* __utl_meta_void_t_h__ */ |