/*!
* \file pack.h
* \brief Template meta-programming parameter pack container
*
* Copyright (C) 2018-2019 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 .
*/
#ifndef __utl_meta_idx_sequence_h__
#define __utl_meta_idx_sequence_h__
#include
#include
/*!
* \ingroup meta
* \defgroup index_sequence
*/
//! @{
namespace utl {
namespace meta {
/*!
* Class template integer_sequence
*/
template
struct integer_sequence {
using value_type = _Tp;
static constexpr size_t size() noexcept {
return sizeof...(_Idx);
}
};
//! Alias template index_sequence
template
using index_sequence = integer_sequence;
//! make_integer_sequence
//! @{
namespace detail {
// Stores a tuple of indices
template struct index_tuple { };
// Concatenates two index_tuples.
template struct it_cat_;
template
struct it_cat_ , index_tuple> {
using type = index_tuple;
};
// Builds an index_tuple<0, 1, 2, ..., _Num-1>.
template
struct make_index_tuple_
: it_cat_>,
eval>>
{ };
// termination specialization for 1
template<>
struct make_index_tuple_<1> {
using type = index_tuple<0>;
};
// termination specialization for 0
template<>
struct make_index_tuple_<0> {
using type = index_tuple<>;
};
// factory type
template>>
struct make_integer_sequence_;
template
struct make_integer_sequence_<_Tp, _Num, index_tuple<_Idx...>> {
static_assert( _Num >= 0,
"Cannot make integer sequence of negative length" );
using type = integer_sequence<_Tp, static_cast<_Tp>(_Idx)...>;
};
}
//! Alias template make_integer_sequence
//! Complexity \f$ O(log N) \f$
template
using make_integer_sequence = eval>;
//! Alias template make_index_sequence
//! Complexity \f$ O(log N) \f$
template
using make_index_sequence = make_integer_sequence;
//! Alias template index_sequence_for
//! Complexity \f$ O(log N) \f$
//! where N is sizeof...(_Ts)
template
using index_sequence_for = make_index_sequence;
//! @}
}}
//! @}
#endif /* __utl_meta_idx_sequence_h__ */