Removed MPL usage from iterator_adaptor.hpp.

This commit is contained in:
Andrey Semashev
2025-02-01 02:03:06 +03:00
parent 4f5f61e37b
commit 1875d95019

View File

@ -7,10 +7,10 @@
#ifndef BOOST_ITERATOR_ADAPTOR_23022003THW_HPP #ifndef BOOST_ITERATOR_ADAPTOR_23022003THW_HPP
#define BOOST_ITERATOR_ADAPTOR_23022003THW_HPP #define BOOST_ITERATOR_ADAPTOR_23022003THW_HPP
#include <boost/core/use_default.hpp>
#include <type_traits> #include <type_traits>
#include <boost/core/use_default.hpp>
#include <boost/iterator/iterator_categories.hpp> #include <boost/iterator/iterator_categories.hpp>
#include <boost/iterator/iterator_facade.hpp> #include <boost/iterator/iterator_facade.hpp>
#include <boost/iterator/iterator_traits.hpp> #include <boost/iterator/iterator_traits.hpp>
@ -25,23 +25,18 @@ namespace iterators {
// explicitly in order to specify that the default should be used. // explicitly in order to specify that the default should be used.
using boost::use_default; using boost::use_default;
} // namespace iterators namespace detail {
namespace iterators {
namespace detail
{
// //
// Result type used in enable_if_convertible meta function. // Result type used in enable_if_convertible meta function.
// This can be an incomplete type, as only pointers to // This can be an incomplete type, as only pointers to
// enable_if_convertible< ... >::type are used. // enable_if_convertible< ... >::type are used.
// We could have used void for this, but conversion to // We could have used void for this, but conversion to
// void* is just to easy. // void* is just too easy.
// //
struct enable_type; struct enable_type;
}
} // namespace detail
// //
// enable_if for use in adapted iterators constructors. // enable_if for use in adapted iterators constructors.
@ -82,81 +77,102 @@ namespace iterators {
// on operator implementation for consequences. // on operator implementation for consequences.
// //
template< typename From, typename To > template< typename From, typename To >
struct enable_if_convertible struct enable_if_convertible :
: std::enable_if< public std::enable_if<
std::is_convertible<From, To>::value std::is_convertible< From, To >::value,
, boost::iterators::detail::enable_type boost::iterators::detail::enable_type
> >
{}; {};
// //
// Default template argument handling for iterator_adaptor // Default template argument handling for iterator_adaptor
// //
namespace detail namespace detail {
{
// If T is use_default, return the result of invoking // If T is use_default, return the result of invoking
// DefaultNullaryFn, otherwise return T. // DefaultNullaryFn, otherwise return T.
template <class T, class DefaultNullaryFn> template< typename T, typename DefaultNullaryFn >
struct ia_dflt_help struct ia_dflt_help
: mpl::eval_if<
std::is_same<T, use_default>
, DefaultNullaryFn
, mpl::identity<T>
>
{ {
using type = T;
}; };
template< typename DefaultNullaryFn >
struct ia_dflt_help< use_default, DefaultNullaryFn >
{
using type = typename DefaultNullaryFn::type;
};
template< typename T, typename DefaultNullaryFn >
using ia_dflt_help_t = typename ia_dflt_help< T, DefaultNullaryFn >::type;
// If T is use_default, return the result of invoking
// DefaultNullaryFn, otherwise - of NondefaultNullaryFn.
template< typename T, typename DefaultNullaryFn, typename NondefaultNullaryFn >
struct ia_eval_if_default
{
using type = typename NondefaultNullaryFn::type;
};
template< typename DefaultNullaryFn, typename NondefaultNullaryFn >
struct ia_eval_if_default< use_default, DefaultNullaryFn, NondefaultNullaryFn >
{
using type = typename DefaultNullaryFn::type;
};
template< typename T, typename DefaultNullaryFn, typename NondefaultNullaryFn >
using ia_eval_if_default_t = typename ia_eval_if_default< T, DefaultNullaryFn, NondefaultNullaryFn >::type;
// A metafunction which computes an iterator_adaptor's base class, // A metafunction which computes an iterator_adaptor's base class,
// a specialization of iterator_facade. // a specialization of iterator_facade.
template< template<
class Derived typename Derived,
, class Base typename Base,
, class Value typename Value,
, class Traversal typename Traversal,
, class Reference typename Reference,
, class Difference typename Difference
> >
struct iterator_adaptor_base using iterator_adaptor_base_t = iterator_facade<
{ Derived,
typedef iterator_facade<
Derived
#ifdef BOOST_ITERATOR_REF_CONSTNESS_KILLS_WRITABILITY #ifdef BOOST_ITERATOR_REF_CONSTNESS_KILLS_WRITABILITY
, typename boost::iterators::detail::ia_dflt_help< detail::ia_dflt_help_t<
Value Value,
, mpl::eval_if< detail::ia_eval_if_default<
std::is_same<Reference,use_default> Reference,
, iterator_value<Base> iterator_value< Base >,
, std::remove_reference<Reference> std::remove_reference< Reference >
> >
>::type >,
#else #else
, typename boost::iterators::detail::ia_dflt_help< detail::ia_dflt_help_t<
Value, iterator_value<Base> Value,
>::type iterator_value< Base >
>,
#endif #endif
, typename boost::iterators::detail::ia_dflt_help< detail::ia_dflt_help_t<
Traversal Traversal,
, iterator_traversal<Base> iterator_traversal< Base >
>::type >,
, typename boost::iterators::detail::ia_dflt_help< detail::ia_dflt_help_t<
Reference Reference,
, mpl::eval_if< detail::ia_eval_if_default<
std::is_same<Value,use_default> Value,
, iterator_reference<Base> iterator_reference< Base >,
, std::add_lvalue_reference<Value> std::add_lvalue_reference< Value >
> >
>::type >,
, typename boost::iterators::detail::ia_dflt_help< detail::ia_dflt_help_t<
Difference, iterator_difference<Base> Difference,
>::type iterator_difference< Base >
> >
type; >;
};
} } // namespace detail
// //
// Iterator Adaptor // Iterator Adaptor
@ -184,49 +200,46 @@ namespace iterators {
// supplied, iterator_traits<Base>::difference_type is used. // supplied, iterator_traits<Base>::difference_type is used.
// //
template< template<
class Derived typename Derived,
, class Base typename Base,
, class Value = use_default typename Value = use_default,
, class Traversal = use_default typename Traversal = use_default,
, class Reference = use_default typename Reference = use_default,
, class Difference = use_default typename Difference = use_default
> >
class iterator_adaptor class iterator_adaptor :
: public boost::iterators::detail::iterator_adaptor_base< public detail::iterator_adaptor_base_t<
Derived, Base, Value, Traversal, Reference, Difference Derived, Base, Value, Traversal, Reference, Difference
>::type >
{ {
friend class iterator_core_access; friend class iterator_core_access;
protected: protected:
typedef typename boost::iterators::detail::iterator_adaptor_base< using super_t = detail::iterator_adaptor_base_t<
Derived, Base, Value, Traversal, Reference, Difference Derived, Base, Value, Traversal, Reference, Difference
>::type super_t; >;
public:
iterator_adaptor() {}
explicit iterator_adaptor(Base const& iter) public:
: m_iterator(iter) using base_type = Base;
iterator_adaptor() = default;
explicit iterator_adaptor(Base const& iter) :
m_iterator(iter)
{ {
} }
typedef Base base_type; base_type const& base() const { return m_iterator; }
Base const& base() const
{ return m_iterator; }
protected: protected:
// for convenience in derived classes // for convenience in derived classes
typedef iterator_adaptor<Derived,Base,Value,Traversal,Reference,Difference> iterator_adaptor_; using iterator_adaptor_ = iterator_adaptor< Derived, Base, Value, Traversal, Reference, Difference >;
// //
// lvalue access to the Base object for Derived // lvalue access to the Base object for Derived
// //
Base const& base_reference() const Base& base_reference() { return m_iterator; }
{ return m_iterator; } Base const& base_reference() const { return m_iterator; }
Base& base_reference()
{ return m_iterator; }
private: private:
// //
@ -235,12 +248,9 @@ namespace iterators {
// will often result in an error. Derived classes should use // will often result in an error. Derived classes should use
// base_reference(), above, to get direct access to m_iterator. // base_reference(), above, to get direct access to m_iterator.
// //
typename super_t::reference dereference() const typename super_t::reference dereference() const { return *m_iterator; }
{ return *m_iterator; }
template < template< typename OtherDerived, typename OtherIterator, typename V, typename C, typename R, typename D >
class OtherDerived, class OtherIterator, class V, class C, class R, class D
>
bool equal(iterator_adaptor< OtherDerived, OtherIterator, V, C, R, D > const& x) const bool equal(iterator_adaptor< OtherDerived, OtherIterator, V, C, R, D > const& x) const
{ {
// Maybe readd with same_distance // Maybe readd with same_distance
@ -250,16 +260,12 @@ namespace iterators {
return m_iterator == x.base(); return m_iterator == x.base();
} }
typedef typename iterator_category_to_traversal< using my_traversal = typename iterator_category_to_traversal< typename super_t::iterator_category >::type;
typename super_t::iterator_category
>::type my_traversal;
void advance(typename super_t::difference_type n) void advance(typename super_t::difference_type n)
{ {
static_assert( static_assert(detail::is_traversal_at_least< my_traversal, random_access_traversal_tag >::value,
std::is_convertible<my_traversal, random_access_traversal_tag>::value, "Iterator must support random access traversal.");
"Iterator must support random access traversal."
);
m_iterator += n; m_iterator += n;
} }
@ -267,23 +273,16 @@ namespace iterators {
void decrement() void decrement()
{ {
static_assert( static_assert(detail::is_traversal_at_least< my_traversal, bidirectional_traversal_tag >::value,
std::is_convertible<my_traversal, bidirectional_traversal_tag>::value, "Iterator must support bidirectional traversal.");
"Iterator must support bidirectional traversal."
);
--m_iterator; --m_iterator;
} }
template < template< typename OtherDerived, typename OtherIterator, typename V, typename C, typename R, typename D >
class OtherDerived, class OtherIterator, class V, class C, class R, class D typename super_t::difference_type distance_to(iterator_adaptor< OtherDerived, OtherIterator, V, C, R, D > const& y) const
>
typename super_t::difference_type distance_to(
iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& y) const
{ {
static_assert( static_assert(detail::is_traversal_at_least< my_traversal, random_access_traversal_tag >::value,
std::is_convertible<my_traversal, random_access_traversal_tag>::value, "Super iterator must support random access traversal.");
"Super iterator must support random access traversal."
);
// Maybe readd with same_distance // Maybe readd with same_distance
// BOOST_STATIC_ASSERT( // BOOST_STATIC_ASSERT(
// (detail::same_category_and_difference<Derived,OtherDerived>::value) // (detail::same_category_and_difference<Derived,OtherDerived>::value)