epoc32/include/stdapis/boost/iterator/counting_iterator.hpp
branchSymbian2
changeset 2 2fe1408b6811
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/epoc32/include/stdapis/boost/iterator/counting_iterator.hpp	Tue Mar 16 16:12:26 2010 +0000
     1.3 @@ -0,0 +1,215 @@
     1.4 +// Copyright David Abrahams 2003.
     1.5 +// Distributed under the Boost Software License, Version 1.0. (See
     1.6 +// accompanying file LICENSE_1_0.txt or copy at
     1.7 +// http://www.boost.org/LICENSE_1_0.txt)
     1.8 +#ifndef COUNTING_ITERATOR_DWA200348_HPP
     1.9 +# define COUNTING_ITERATOR_DWA200348_HPP
    1.10 +
    1.11 +# include <boost/iterator/iterator_adaptor.hpp>
    1.12 +# include <boost/detail/numeric_traits.hpp>
    1.13 +# include <boost/mpl/bool.hpp>
    1.14 +# include <boost/mpl/if.hpp>
    1.15 +# include <boost/mpl/identity.hpp>
    1.16 +# include <boost/mpl/eval_if.hpp>
    1.17 +
    1.18 +namespace boost {
    1.19 +
    1.20 +template <
    1.21 +    class Incrementable
    1.22 +  , class CategoryOrTraversal
    1.23 +  , class Difference
    1.24 +>
    1.25 +class counting_iterator;
    1.26 +
    1.27 +namespace detail
    1.28 +{
    1.29 +  // Try to detect numeric types at compile time in ways compatible
    1.30 +  // with the limitations of the compiler and library.
    1.31 +  template <class T>
    1.32 +  struct is_numeric_impl
    1.33 +  {
    1.34 +      // For a while, this wasn't true, but we rely on it below. This is a regression assert.
    1.35 +      BOOST_STATIC_ASSERT(::boost::is_integral<char>::value);
    1.36 +      
    1.37 +# ifndef BOOST_NO_LIMITS_COMPILE_TIME_CONSTANTS
    1.38 +      
    1.39 +      BOOST_STATIC_CONSTANT(bool, value = std::numeric_limits<T>::is_specialized);
    1.40 +      
    1.41 +# else
    1.42 +      
    1.43 +#  if !BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x551))
    1.44 +      BOOST_STATIC_CONSTANT(
    1.45 +          bool, value = (
    1.46 +              boost::is_convertible<int,T>::value
    1.47 +           && boost::is_convertible<T,int>::value
    1.48 +      ));
    1.49 +#  else
    1.50 +    BOOST_STATIC_CONSTANT(bool, value = ::boost::is_arithmetic<T>::value);
    1.51 +#  endif
    1.52 +      
    1.53 +# endif
    1.54 +  };
    1.55 +
    1.56 +  template <class T>
    1.57 +  struct is_numeric
    1.58 +    : mpl::bool_<(::boost::detail::is_numeric_impl<T>::value)>
    1.59 +  {};
    1.60 +
    1.61 +#  if defined(BOOST_HAS_LONG_LONG)
    1.62 +  template <>
    1.63 +  struct is_numeric< ::boost::long_long_type>
    1.64 +    : mpl::true_ {};
    1.65 +  
    1.66 +  template <>
    1.67 +  struct is_numeric< ::boost::ulong_long_type>
    1.68 +    : mpl::true_ {};
    1.69 +#  endif
    1.70 +
    1.71 +  // Some compilers fail to have a numeric_limits specialization
    1.72 +  template <>
    1.73 +  struct is_numeric<wchar_t>
    1.74 +    : mpl::true_ {};
    1.75 +  
    1.76 +  template <class T>
    1.77 +  struct numeric_difference
    1.78 +  {
    1.79 +      typedef typename boost::detail::numeric_traits<T>::difference_type type;
    1.80 +  };
    1.81 +
    1.82 +  BOOST_STATIC_ASSERT(is_numeric<int>::value);
    1.83 +  
    1.84 +  template <class Incrementable, class CategoryOrTraversal, class Difference>
    1.85 +  struct counting_iterator_base
    1.86 +  {
    1.87 +      typedef typename detail::ia_dflt_help<
    1.88 +          CategoryOrTraversal
    1.89 +        , mpl::eval_if<
    1.90 +              is_numeric<Incrementable>
    1.91 +            , mpl::identity<random_access_traversal_tag>
    1.92 +            , iterator_traversal<Incrementable>
    1.93 +          >
    1.94 +      >::type traversal;
    1.95 +      
    1.96 +      typedef typename detail::ia_dflt_help<
    1.97 +          Difference
    1.98 +        , mpl::eval_if<
    1.99 +              is_numeric<Incrementable>
   1.100 +            , numeric_difference<Incrementable>
   1.101 +            , iterator_difference<Incrementable>
   1.102 +          >
   1.103 +      >::type difference;
   1.104 +      
   1.105 +      typedef iterator_adaptor<
   1.106 +          counting_iterator<Incrementable, CategoryOrTraversal, Difference> // self
   1.107 +        , Incrementable                                           // Base
   1.108 +        , Incrementable                                           // Value
   1.109 +# ifndef BOOST_ITERATOR_REF_CONSTNESS_KILLS_WRITABILITY
   1.110 +          const  // MSVC won't strip this.  Instead we enable Thomas'
   1.111 +                 // criterion (see boost/iterator/detail/facade_iterator_category.hpp)
   1.112 +# endif 
   1.113 +        , traversal
   1.114 +        , Incrementable const&                                    // reference
   1.115 +        , difference
   1.116 +      > type;
   1.117 +  };
   1.118 +
   1.119 +  // Template class distance_policy_select -- choose a policy for computing the
   1.120 +  // distance between counting_iterators at compile-time based on whether or not
   1.121 +  // the iterator wraps an integer or an iterator, using "poor man's partial
   1.122 +  // specialization".
   1.123 +
   1.124 +  template <bool is_integer> struct distance_policy_select;
   1.125 +
   1.126 +  // A policy for wrapped iterators
   1.127 +  template <class Difference, class Incrementable1, class Incrementable2>
   1.128 +  struct iterator_distance
   1.129 +  {
   1.130 +      static Difference distance(Incrementable1 x, Incrementable2 y)
   1.131 +      {
   1.132 +          return y - x;
   1.133 +      }
   1.134 +  };
   1.135 +
   1.136 +  // A policy for wrapped numbers
   1.137 +  template <class Difference, class Incrementable1, class Incrementable2>
   1.138 +  struct number_distance
   1.139 +  {
   1.140 +      static Difference distance(Incrementable1 x, Incrementable2 y)
   1.141 +      {
   1.142 +          return numeric_distance(x, y);
   1.143 +      }
   1.144 +  };
   1.145 +}
   1.146 +
   1.147 +template <
   1.148 +    class Incrementable
   1.149 +  , class CategoryOrTraversal = use_default
   1.150 +  , class Difference = use_default
   1.151 +>
   1.152 +class counting_iterator
   1.153 +  : public detail::counting_iterator_base<
   1.154 +        Incrementable, CategoryOrTraversal, Difference
   1.155 +    >::type
   1.156 +{
   1.157 +    typedef typename detail::counting_iterator_base<
   1.158 +        Incrementable, CategoryOrTraversal, Difference
   1.159 +    >::type super_t;
   1.160 +    
   1.161 +    friend class iterator_core_access;
   1.162 +
   1.163 + public:
   1.164 +    typedef typename super_t::difference_type difference_type;
   1.165 +
   1.166 +    counting_iterator() { }
   1.167 +    
   1.168 +    counting_iterator(counting_iterator const& rhs) : super_t(rhs.base()) {}
   1.169 +
   1.170 +    counting_iterator(Incrementable x)
   1.171 +      : super_t(x)
   1.172 +    {
   1.173 +    }
   1.174 +
   1.175 +# if 0
   1.176 +    template<class OtherIncrementable>
   1.177 +    counting_iterator(
   1.178 +        counting_iterator<OtherIncrementable, CategoryOrTraversal, Difference> const& t
   1.179 +      , typename enable_if_convertible<OtherIncrementable, Incrementable>::type* = 0
   1.180 +    )
   1.181 +      : super_t(t.base())
   1.182 +    {}
   1.183 +# endif 
   1.184 +
   1.185 + private:
   1.186 +    
   1.187 +    typename super_t::reference dereference() const
   1.188 +    {
   1.189 +        return this->base_reference();
   1.190 +    }
   1.191 +
   1.192 +    template <class OtherIncrementable>
   1.193 +    difference_type
   1.194 +    distance_to(counting_iterator<OtherIncrementable, CategoryOrTraversal, Difference> const& y) const
   1.195 +    {
   1.196 +      typedef typename mpl::if_<
   1.197 +          detail::is_numeric<Incrementable>
   1.198 +        , detail::number_distance<difference_type, Incrementable, OtherIncrementable>
   1.199 +        , detail::iterator_distance<difference_type, Incrementable, OtherIncrementable>
   1.200 +      >::type d;
   1.201 +
   1.202 +      return d::distance(this->base(), y.base());
   1.203 +    }
   1.204 +};
   1.205 +
   1.206 +// Manufacture a counting iterator for an arbitrary incrementable type
   1.207 +template <class Incrementable>
   1.208 +inline counting_iterator<Incrementable>
   1.209 +make_counting_iterator(Incrementable x)
   1.210 +{
   1.211 +  typedef counting_iterator<Incrementable> result_t;
   1.212 +  return result_t(x);
   1.213 +}
   1.214 +
   1.215 +
   1.216 +} // namespace boost::iterator
   1.217 +
   1.218 +#endif // COUNTING_ITERATOR_DWA200348_HPP