1 /*============================================================================= 2 Copyright (c) 2001-2011 Joel de Guzman 3 4 Distributed under the Boost Software License, Version 1.0. (See accompanying 5 file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) 6 ==============================================================================*/ 7 #if !defined(FUSION_ADVANCE_09172005_1146) 8 #define FUSION_ADVANCE_09172005_1146 9 10 #include <boost/fusion/support/config.hpp> 11 #include <boost/fusion/iterator/detail/advance.hpp> 12 #include <boost/fusion/support/category_of.hpp> 13 14 #include <boost/mpl/int.hpp> 15 #include <boost/mpl/assert.hpp> 16 #include <boost/type_traits/is_same.hpp> 17 #include <boost/fusion/support/tag_of.hpp> 18 19 namespace boost { namespace fusion 20 { 21 struct random_access_traversal_tag; 22 23 // Special tags: 24 struct iterator_facade_tag; // iterator facade tag 25 struct boost_array_iterator_tag; // boost::array iterator tag 26 struct mpl_iterator_tag; // mpl sequence iterator tag 27 struct std_pair_iterator_tag; // std::pair iterator tag 28 29 namespace extension 30 { 31 template <typename Tag> 32 struct advance_impl 33 { 34 // default implementation 35 template <typename Iterator, typename N> 36 struct apply : 37 mpl::if_c< 38 (N::value > 0) 39 , advance_detail::forward<Iterator, N::value> 40 , advance_detail::backward<Iterator, N::value> 41 >::type 42 { 43 BOOST_MPL_ASSERT_NOT((traits::is_random_access<Iterator>)); 44 }; 45 }; 46 47 template <> 48 struct advance_impl<iterator_facade_tag> 49 { 50 template <typename Iterator, typename N> 51 struct apply : Iterator::template advance<Iterator, N> {}; 52 }; 53 54 template <> 55 struct advance_impl<boost_array_iterator_tag>; 56 57 template <> 58 struct advance_impl<mpl_iterator_tag>; 59 60 template <> 61 struct advance_impl<std_pair_iterator_tag>; 62 } 63 64 namespace result_of 65 { 66 template <typename Iterator, int N> 67 struct advance_c 68 : extension::advance_impl<typename detail::tag_of<Iterator>::type>::template apply<Iterator, mpl::int_<N> > 69 {}; 70 71 template <typename Iterator, typename N> 72 struct advance 73 : extension::advance_impl<typename detail::tag_of<Iterator>::type>::template apply<Iterator, N> 74 {}; 75 } 76 77 template <int N, typename Iterator> 78 BOOST_CONSTEXPR BOOST_FUSION_GPU_ENABLED 79 inline typename result_of::advance_c<Iterator, N>::type const advance_c(Iterator const & i)80 advance_c(Iterator const& i) 81 { 82 return result_of::advance_c<Iterator, N>::call(i); 83 } 84 85 template<typename N, typename Iterator> 86 BOOST_CONSTEXPR BOOST_FUSION_GPU_ENABLED 87 inline typename result_of::advance<Iterator, N>::type const advance(Iterator const & i)88 advance(Iterator const& i) 89 { 90 return result_of::advance<Iterator, N>::call(i); 91 } 92 93 }} // namespace boost::fusion 94 95 #endif 96