1 2 #ifndef BOOST_MPL_PAIR_VIEW_HPP_INCLUDED 3 #define BOOST_MPL_PAIR_VIEW_HPP_INCLUDED 4 5 // Copyright David Abrahams 2003-2004 6 // Copyright Aleksey Gurtovoy 2004 7 // 8 // Distributed under the Boost Software License, Version 1.0. 9 // (See accompanying file LICENSE_1_0.txt or copy at 10 // http://www.boost.org/LICENSE_1_0.txt) 11 // 12 // See http://www.boost.org/libs/mpl for documentation. 13 14 // $Id$ 15 // $Date$ 16 // $Revision$ 17 18 #include <boost/mpl/begin_end.hpp> 19 #include <boost/mpl/iterator_category.hpp> 20 #include <boost/mpl/advance.hpp> 21 #include <boost/mpl/distance.hpp> 22 #include <boost/mpl/next_prior.hpp> 23 #include <boost/mpl/deref.hpp> 24 #include <boost/mpl/min_max.hpp> 25 #include <boost/mpl/pair.hpp> 26 #include <boost/mpl/iterator_tags.hpp> 27 #include <boost/mpl/aux_/config/ctps.hpp> 28 #include <boost/mpl/aux_/na_spec.hpp> 29 30 namespace boost { namespace mpl { 31 32 namespace aux { 33 struct pair_iter_tag; 34 35 #if defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) 36 37 template< typename Iter1, typename Iter2, typename Category > 38 struct pair_iter; 39 40 template< typename Category > struct prior_pair_iter 41 { 42 template< typename Iter1, typename Iter2 > struct apply 43 { 44 typedef typename mpl::prior<Iter1>::type i1_; 45 typedef typename mpl::prior<Iter2>::type i2_; 46 typedef pair_iter<i1_,i2_,Category> type; 47 }; 48 }; 49 50 template<> struct prior_pair_iter<forward_iterator_tag> 51 { 52 template< typename Iter1, typename Iter2 > struct apply 53 { 54 typedef pair_iter<Iter1,Iter2,forward_iterator_tag> type; 55 }; 56 }; 57 58 #endif 59 } 60 61 template< 62 typename Iter1 63 , typename Iter2 64 , typename Category 65 > 66 struct pair_iter 67 { 68 typedef aux::pair_iter_tag tag; 69 typedef Category category; 70 typedef Iter1 first; 71 typedef Iter2 second; 72 73 #if defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) 74 typedef pair< 75 typename deref<Iter1>::type 76 , typename deref<Iter2>::type 77 > type; 78 79 typedef typename mpl::next<Iter1>::type i1_; 80 typedef typename mpl::next<Iter2>::type i2_; 81 typedef pair_iter<i1_,i2_,Category> next; 82 83 typedef apply_wrap2< aux::prior_pair_iter<Category>,Iter1,Iter2 >::type prior; 84 #endif 85 }; 86 87 88 #if !defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) 89 90 template< typename Iter1, typename Iter2, typename C > 91 struct deref< pair_iter<Iter1,Iter2,C> > 92 { 93 typedef pair< 94 typename deref<Iter1>::type 95 , typename deref<Iter2>::type 96 > type; 97 }; 98 99 template< typename Iter1, typename Iter2, typename C > 100 struct next< pair_iter<Iter1,Iter2,C> > 101 { 102 typedef typename mpl::next<Iter1>::type i1_; 103 typedef typename mpl::next<Iter2>::type i2_; 104 typedef pair_iter<i1_,i2_,C> type; 105 }; 106 107 template< typename Iter1, typename Iter2, typename C > 108 struct prior< pair_iter<Iter1,Iter2,C> > 109 { 110 typedef typename mpl::prior<Iter1>::type i1_; 111 typedef typename mpl::prior<Iter2>::type i2_; 112 typedef pair_iter<i1_,i2_,C> type; 113 }; 114 115 #endif // BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION 116 117 118 template<> struct advance_impl<aux::pair_iter_tag> 119 { 120 template< typename Iter, typename D > struct apply 121 { 122 typedef typename mpl::advance< typename Iter::first,D >::type i1_; 123 typedef typename mpl::advance< typename Iter::second,D >::type i2_; 124 typedef pair_iter<i1_,i2_,typename Iter::category> type; 125 }; 126 }; 127 128 template<> struct distance_impl<aux::pair_iter_tag> 129 { 130 template< typename Iter1, typename Iter2 > struct apply 131 { 132 // agurt, 10/nov/04: MSVC 6.5 ICE-s on forwarding 133 typedef typename mpl::distance< 134 typename first<Iter1>::type 135 , typename first<Iter2>::type 136 >::type type; 137 }; 138 }; 139 140 141 template< 142 typename BOOST_MPL_AUX_NA_PARAM(Sequence1) 143 , typename BOOST_MPL_AUX_NA_PARAM(Sequence2) 144 > 145 struct pair_view 146 { 147 typedef nested_begin_end_tag tag; 148 149 typedef typename begin<Sequence1>::type iter1_; 150 typedef typename begin<Sequence2>::type iter2_; 151 typedef typename min< 152 typename iterator_category<iter1_>::type 153 , typename iterator_category<iter2_>::type 154 >::type category_; 155 156 typedef pair_iter<iter1_,iter2_,category_> begin; 157 158 typedef pair_iter< 159 typename end<Sequence1>::type 160 , typename end<Sequence2>::type 161 , category_ 162 > end; 163 }; 164 165 BOOST_MPL_AUX_NA_SPEC(2, pair_view) 166 167 }} 168 169 #endif // BOOST_MPL_PAIR_VIEW_HPP_INCLUDED 170