1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/epoc32/include/stdapis/boost/iterator/iterator_adaptor.hpp Tue Mar 16 16:12:26 2010 +0000
1.3 @@ -0,0 +1,366 @@
1.4 +// (C) Copyright David Abrahams 2002.
1.5 +// (C) Copyright Jeremy Siek 2002.
1.6 +// (C) Copyright Thomas Witt 2002.
1.7 +// Distributed under the Boost Software License, Version 1.0. (See
1.8 +// accompanying file LICENSE_1_0.txt or copy at
1.9 +// http://www.boost.org/LICENSE_1_0.txt)
1.10 +#ifndef BOOST_ITERATOR_ADAPTOR_23022003THW_HPP
1.11 +#define BOOST_ITERATOR_ADAPTOR_23022003THW_HPP
1.12 +
1.13 +#include <boost/static_assert.hpp>
1.14 +#include <boost/iterator.hpp>
1.15 +#include <boost/detail/iterator.hpp>
1.16 +
1.17 +#include <boost/iterator/iterator_categories.hpp>
1.18 +#include <boost/iterator/iterator_facade.hpp>
1.19 +#include <boost/iterator/detail/enable_if.hpp>
1.20 +
1.21 +#include <boost/mpl/and.hpp>
1.22 +#include <boost/mpl/not.hpp>
1.23 +#include <boost/mpl/or.hpp>
1.24 +
1.25 +#include <boost/type_traits/is_same.hpp>
1.26 +#include <boost/type_traits/is_convertible.hpp>
1.27 +
1.28 +#ifdef BOOST_ITERATOR_REF_CONSTNESS_KILLS_WRITABILITY
1.29 +# include <boost/type_traits/remove_reference.hpp>
1.30 +#else
1.31 +# include <boost/type_traits/add_reference.hpp>
1.32 +#endif
1.33 +
1.34 +#include <boost/iterator/detail/config_def.hpp>
1.35 +
1.36 +#include <boost/iterator/iterator_traits.hpp>
1.37 +
1.38 +namespace boost
1.39 +{
1.40 + // Used as a default template argument internally, merely to
1.41 + // indicate "use the default", this can also be passed by users
1.42 + // explicitly in order to specify that the default should be used.
1.43 + struct use_default;
1.44 +
1.45 +# ifndef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION
1.46 + // the incompleteness of use_default causes massive problems for
1.47 + // is_convertible (naturally). This workaround is fortunately not
1.48 + // needed for vc6/vc7.
1.49 + template<class To>
1.50 + struct is_convertible<use_default,To>
1.51 + : mpl::false_ {};
1.52 +# endif
1.53 +
1.54 + namespace detail
1.55 + {
1.56 +
1.57 + //
1.58 + // Result type used in enable_if_convertible meta function.
1.59 + // This can be an incomplete type, as only pointers to
1.60 + // enable_if_convertible< ... >::type are used.
1.61 + // We could have used void for this, but conversion to
1.62 + // void* is just to easy.
1.63 + //
1.64 + struct enable_type;
1.65 + }
1.66 +
1.67 +
1.68 + //
1.69 + // enable_if for use in adapted iterators constructors.
1.70 + //
1.71 + // In order to provide interoperability between adapted constant and
1.72 + // mutable iterators, adapted iterators will usually provide templated
1.73 + // conversion constructors of the following form
1.74 + //
1.75 + // template <class BaseIterator>
1.76 + // class adapted_iterator :
1.77 + // public iterator_adaptor< adapted_iterator<Iterator>, Iterator >
1.78 + // {
1.79 + // public:
1.80 + //
1.81 + // ...
1.82 + //
1.83 + // template <class OtherIterator>
1.84 + // adapted_iterator(
1.85 + // OtherIterator const& it
1.86 + // , typename enable_if_convertible<OtherIterator, Iterator>::type* = 0);
1.87 + //
1.88 + // ...
1.89 + // };
1.90 + //
1.91 + // enable_if_convertible is used to remove those overloads from the overload
1.92 + // set that cannot be instantiated. For all practical purposes only overloads
1.93 + // for constant/mutable interaction will remain. This has the advantage that
1.94 + // meta functions like boost::is_convertible do not return false positives,
1.95 + // as they can only look at the signature of the conversion constructor
1.96 + // and not at the actual instantiation.
1.97 + //
1.98 + // enable_if_interoperable can be safely used in user code. It falls back to
1.99 + // always enabled for compilers that don't support enable_if or is_convertible.
1.100 + // There is no need for compiler specific workarounds in user code.
1.101 + //
1.102 + // The operators implementation relies on boost::is_convertible not returning
1.103 + // false positives for user/library defined iterator types. See comments
1.104 + // on operator implementation for consequences.
1.105 + //
1.106 +# if BOOST_WORKAROUND(BOOST_MSVC, <= 1300)
1.107 +
1.108 + template<typename From, typename To>
1.109 + struct enable_if_convertible
1.110 + {
1.111 + typedef typename mpl::if_<
1.112 + mpl::or_<
1.113 + is_same<From,To>
1.114 + , is_convertible<From, To>
1.115 + >
1.116 + , detail::enable_type
1.117 + , int&
1.118 + >::type type;
1.119 + };
1.120 +
1.121 +# elif defined(BOOST_NO_IS_CONVERTIBLE) || defined(BOOST_NO_SFINAE)
1.122 +
1.123 + template <class From, class To>
1.124 + struct enable_if_convertible
1.125 + {
1.126 + typedef detail::enable_type type;
1.127 + };
1.128 +
1.129 +# elif BOOST_WORKAROUND(_MSC_FULL_VER, BOOST_TESTED_AT(13102292)) && BOOST_MSVC > 1300
1.130 +
1.131 + // For some reason vc7.1 needs us to "cut off" instantiation
1.132 + // of is_convertible in a few cases.
1.133 + template<typename From, typename To>
1.134 + struct enable_if_convertible
1.135 + : iterators::enable_if<
1.136 + mpl::or_<
1.137 + is_same<From,To>
1.138 + , is_convertible<From, To>
1.139 + >
1.140 + , detail::enable_type
1.141 + >
1.142 + {};
1.143 +
1.144 +# else
1.145 +
1.146 + template<typename From, typename To>
1.147 + struct enable_if_convertible
1.148 + : iterators::enable_if<
1.149 + is_convertible<From, To>
1.150 + , detail::enable_type
1.151 + >
1.152 + {};
1.153 +
1.154 +# endif
1.155 +
1.156 + //
1.157 + // Default template argument handling for iterator_adaptor
1.158 + //
1.159 + namespace detail
1.160 + {
1.161 + // If T is use_default, return the result of invoking
1.162 + // DefaultNullaryFn, otherwise return T.
1.163 + template <class T, class DefaultNullaryFn>
1.164 + struct ia_dflt_help
1.165 + : mpl::eval_if<
1.166 + is_same<T, use_default>
1.167 + , DefaultNullaryFn
1.168 + , mpl::identity<T>
1.169 + >
1.170 + {
1.171 + };
1.172 +
1.173 + // A metafunction which computes an iterator_adaptor's base class,
1.174 + // a specialization of iterator_facade.
1.175 + template <
1.176 + class Derived
1.177 + , class Base
1.178 + , class Value
1.179 + , class Traversal
1.180 + , class Reference
1.181 + , class Difference
1.182 + >
1.183 + struct iterator_adaptor_base
1.184 + {
1.185 + typedef iterator_facade<
1.186 + Derived
1.187 +
1.188 +# ifdef BOOST_ITERATOR_REF_CONSTNESS_KILLS_WRITABILITY
1.189 + , typename detail::ia_dflt_help<
1.190 + Value
1.191 + , mpl::eval_if<
1.192 + is_same<Reference,use_default>
1.193 + , iterator_value<Base>
1.194 + , remove_reference<Reference>
1.195 + >
1.196 + >::type
1.197 +# else
1.198 + , typename detail::ia_dflt_help<
1.199 + Value, iterator_value<Base>
1.200 + >::type
1.201 +# endif
1.202 +
1.203 + , typename detail::ia_dflt_help<
1.204 + Traversal
1.205 + , iterator_traversal<Base>
1.206 + >::type
1.207 +
1.208 + , typename detail::ia_dflt_help<
1.209 + Reference
1.210 + , mpl::eval_if<
1.211 + is_same<Value,use_default>
1.212 + , iterator_reference<Base>
1.213 + , add_reference<Value>
1.214 + >
1.215 + >::type
1.216 +
1.217 + , typename detail::ia_dflt_help<
1.218 + Difference, iterator_difference<Base>
1.219 + >::type
1.220 + >
1.221 + type;
1.222 + };
1.223 +
1.224 + // workaround for aC++ CR JAGaf33512
1.225 + template <class Tr1, class Tr2>
1.226 + inline void iterator_adaptor_assert_traversal ()
1.227 + {
1.228 + BOOST_STATIC_ASSERT((is_convertible<Tr1, Tr2>::value));
1.229 + }
1.230 + }
1.231 +
1.232 + //
1.233 + // Iterator Adaptor
1.234 + //
1.235 + // The parameter ordering changed slightly with respect to former
1.236 + // versions of iterator_adaptor The idea is that when the user needs
1.237 + // to fiddle with the reference type it is highly likely that the
1.238 + // iterator category has to be adjusted as well. Any of the
1.239 + // following four template arguments may be ommitted or explicitly
1.240 + // replaced by use_default.
1.241 + //
1.242 + // Value - if supplied, the value_type of the resulting iterator, unless
1.243 + // const. If const, a conforming compiler strips constness for the
1.244 + // value_type. If not supplied, iterator_traits<Base>::value_type is used
1.245 + //
1.246 + // Category - the traversal category of the resulting iterator. If not
1.247 + // supplied, iterator_traversal<Base>::type is used.
1.248 + //
1.249 + // Reference - the reference type of the resulting iterator, and in
1.250 + // particular, the result type of operator*(). If not supplied but
1.251 + // Value is supplied, Value& is used. Otherwise
1.252 + // iterator_traits<Base>::reference is used.
1.253 + //
1.254 + // Difference - the difference_type of the resulting iterator. If not
1.255 + // supplied, iterator_traits<Base>::difference_type is used.
1.256 + //
1.257 + template <
1.258 + class Derived
1.259 + , class Base
1.260 + , class Value = use_default
1.261 + , class Traversal = use_default
1.262 + , class Reference = use_default
1.263 + , class Difference = use_default
1.264 + >
1.265 + class iterator_adaptor
1.266 + : public detail::iterator_adaptor_base<
1.267 + Derived, Base, Value, Traversal, Reference, Difference
1.268 + >::type
1.269 + {
1.270 + friend class iterator_core_access;
1.271 +
1.272 + protected:
1.273 + typedef typename detail::iterator_adaptor_base<
1.274 + Derived, Base, Value, Traversal, Reference, Difference
1.275 + >::type super_t;
1.276 + public:
1.277 + iterator_adaptor() {}
1.278 +
1.279 + explicit iterator_adaptor(Base const &iter)
1.280 + : m_iterator(iter)
1.281 + {
1.282 + }
1.283 +
1.284 + typedef Base base_type;
1.285 +
1.286 + Base const& base() const
1.287 + { return m_iterator; }
1.288 +
1.289 + protected:
1.290 + // for convenience in derived classes
1.291 + typedef iterator_adaptor<Derived,Base,Value,Traversal,Reference,Difference> iterator_adaptor_;
1.292 +
1.293 + //
1.294 + // lvalue access to the Base object for Derived
1.295 + //
1.296 + Base const& base_reference() const
1.297 + { return m_iterator; }
1.298 +
1.299 + Base& base_reference()
1.300 + { return m_iterator; }
1.301 +
1.302 + private:
1.303 + //
1.304 + // Core iterator interface for iterator_facade. This is private
1.305 + // to prevent temptation for Derived classes to use it, which
1.306 + // will often result in an error. Derived classes should use
1.307 + // base_reference(), above, to get direct access to m_iterator.
1.308 + //
1.309 + typename super_t::reference dereference() const
1.310 + { return *m_iterator; }
1.311 +
1.312 + template <
1.313 + class OtherDerived, class OtherIterator, class V, class C, class R, class D
1.314 + >
1.315 + bool equal(iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& x) const
1.316 + {
1.317 + // Maybe readd with same_distance
1.318 + // BOOST_STATIC_ASSERT(
1.319 + // (detail::same_category_and_difference<Derived,OtherDerived>::value)
1.320 + // );
1.321 + return m_iterator == x.base();
1.322 + }
1.323 +
1.324 + typedef typename iterator_category_to_traversal<
1.325 + typename super_t::iterator_category
1.326 + >::type my_traversal;
1.327 +
1.328 +# define BOOST_ITERATOR_ADAPTOR_ASSERT_TRAVERSAL(cat) \
1.329 + detail::iterator_adaptor_assert_traversal<my_traversal, cat>();
1.330 +
1.331 + void advance(typename super_t::difference_type n)
1.332 + {
1.333 + BOOST_ITERATOR_ADAPTOR_ASSERT_TRAVERSAL(random_access_traversal_tag)
1.334 + m_iterator += n;
1.335 + }
1.336 +
1.337 + void increment() { ++m_iterator; }
1.338 +
1.339 + void decrement()
1.340 + {
1.341 + BOOST_ITERATOR_ADAPTOR_ASSERT_TRAVERSAL(bidirectional_traversal_tag)
1.342 + --m_iterator;
1.343 + }
1.344 +
1.345 + template <
1.346 + class OtherDerived, class OtherIterator, class V, class C, class R, class D
1.347 + >
1.348 + typename super_t::difference_type distance_to(
1.349 + iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& y) const
1.350 + {
1.351 + BOOST_ITERATOR_ADAPTOR_ASSERT_TRAVERSAL(random_access_traversal_tag)
1.352 + // Maybe readd with same_distance
1.353 + // BOOST_STATIC_ASSERT(
1.354 + // (detail::same_category_and_difference<Derived,OtherDerived>::value)
1.355 + // );
1.356 + return y.base() - m_iterator;
1.357 + }
1.358 +
1.359 +# undef BOOST_ITERATOR_ADAPTOR_ASSERT_TRAVERSAL
1.360 +
1.361 + private: // data members
1.362 + Base m_iterator;
1.363 + };
1.364 +
1.365 +} // namespace boost
1.366 +
1.367 +#include <boost/iterator/detail/config_undef.hpp>
1.368 +
1.369 +#endif // BOOST_ITERATOR_ADAPTOR_23022003THW_HPP