]> git.donarmstrong.com Git - rsem.git/blob - boost/fusion/container/list/detail/at_impl.hpp
Updated boost to v1.55.0
[rsem.git] / boost / fusion / container / list / detail / at_impl.hpp
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_AT_IMPL_07172005_0726)
8 #define FUSION_AT_IMPL_07172005_0726
9
10 #include <boost/fusion/support/detail/access.hpp>
11 #include <boost/type_traits/is_const.hpp>
12 #include <boost/type_traits/add_const.hpp>
13 #include <boost/mpl/if.hpp>
14 #include <boost/mpl/bool.hpp>
15
16 namespace boost { namespace fusion
17 {
18     namespace detail
19     {
20         template <typename Cons>
21         struct cons_deref
22         {
23             typedef typename Cons::car_type type;
24         };
25
26         template <typename Cons, int I>
27         struct cons_advance
28         {
29             typedef typename
30                 cons_advance<Cons, I-1>::type::cdr_type
31             type;
32         };
33
34         template <typename Cons>
35         struct cons_advance<Cons, 0>
36         {
37             typedef Cons type;
38         };
39
40         template <typename Cons>
41         struct cons_advance<Cons, 1>
42         {
43             typedef typename Cons::cdr_type type;
44         };
45
46         template <typename Cons>
47         struct cons_advance<Cons, 2>
48         {
49 #if BOOST_WORKAROUND(BOOST_MSVC, > 1400) // VC8 and above
50             typedef typename Cons::cdr_type::cdr_type type;
51 #else
52             typedef typename Cons::cdr_type _a;
53             typedef typename _a::cdr_type type;
54 #endif
55         };
56
57         template <typename Cons>
58         struct cons_advance<Cons, 3>
59         {
60 #if BOOST_WORKAROUND(BOOST_MSVC, > 1400) // VC8 and above
61             typedef typename Cons::cdr_type::cdr_type::cdr_type type;
62 #else
63             typedef typename Cons::cdr_type _a;
64             typedef typename _a::cdr_type _b;
65             typedef typename _b::cdr_type type;
66 #endif
67         };
68
69         template <typename Cons>
70         struct cons_advance<Cons, 4>
71         {
72 #if BOOST_WORKAROUND(BOOST_MSVC, > 1400) // VC8 and above
73             typedef typename Cons::cdr_type::cdr_type::cdr_type::cdr_type type;
74 #else
75             typedef typename Cons::cdr_type _a;
76             typedef typename _a::cdr_type _b;
77             typedef typename _b::cdr_type _c;
78             typedef typename _c::cdr_type type;
79 #endif
80         };
81     }
82
83     struct cons_tag;
84
85     namespace extension
86     {
87         template <typename Tag>
88         struct at_impl;
89
90         template <>
91         struct at_impl<cons_tag>
92         {
93             template <typename Sequence, typename N>
94             struct apply
95             {
96                 typedef typename detail::cons_deref<
97                     typename detail::cons_advance<Sequence, N::value>::type>::type
98                 element;
99
100                 typedef typename
101                     mpl::if_<
102                         is_const<Sequence>
103                       , typename detail::cref_result<element>::type
104                       , typename detail::ref_result<element>::type
105                     >::type
106                 type;
107
108                 template <typename Cons, int N2>
109                 static type
110                 call(Cons& s, mpl::int_<N2>)
111                 {
112                     return call(s.cdr, mpl::int_<N2-1>());
113                 }
114
115                 template <typename Cons>
116                 static type
117                 call(Cons& s, mpl::int_<0>)
118                 {
119                     return s.car;
120                 }
121
122                 static type
123                 call(Sequence& s)
124                 {
125                     return call(s, mpl::int_<N::value>());
126                 }
127             };
128         };
129     }
130 }}
131
132 #endif