libqi-api  2.4.3.28
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
bindtype.hxx
Go to the documentation of this file.
1 #pragma once
2 /*
3 ** Copyright (C) 2013, 2014 Aldebaran Robotics
4 ** See COPYING for the license
5 */
6 
7 #ifndef _QITYPE_DETAILS_BINDTYPE_HXX_
8 #define _QITYPE_DETAILS_BINDTYPE_HXX_
9 
10 #include <boost/mpl/find_if.hpp>
11 #include <boost/mpl/vector.hpp>
12 #include <boost/mpl/at.hpp>
13 #include <boost/mpl/placeholders.hpp>
14 #include <boost/mpl/max_element.hpp>
15 #include <boost/mpl/transform.hpp>
16 #include <boost/function_types/parameter_types.hpp>
17 #include <boost/function_types/function_type.hpp>
18 #include <boost/function_types/function_pointer.hpp>
19 #include <boost/bind.hpp>
20 #include <boost/any.hpp>
21 
22 namespace qi
23 {
24  namespace detail
25  {
26  // Support stuff for boost_bind_function_type
27 
28  class ignore{};
29 
30  // Just store an int and a type
31  template<int I, typename P>
32  struct MappingItem {};
33 
34  // IntFromMappingItem: Extract int from MappingItem or something else
35 
36  template<typename T>
38  {
39  static const long value = 0;
40  };
41 
42  template<int I, typename P>
44  {
45  static const long value = I;
46  };
47 
48 
49  // ArgResolver: Take a function, an index, and a boost::_bi::list element
50  // return ignore, or a MappingItem
51 
52  template<typename F, int P, typename bilistarg>
53  struct ArgResolver
54  {
55  };
56 
57  template<typename F, int P, typename V>
58  struct ArgResolver<F, P, boost::_bi::value<V> >
59  {
60  typedef ignore type;
61  };
62 
63  template<typename F, int P, int I>
64  struct ArgResolver<F, P, boost::arg<I> >
65  {
66  typedef MappingItem<I,
67  typename boost::mpl::at_c<
68  typename boost::function_types::parameter_types<F>::type,
69  P
70  >::type
71  > type;
72  };
73 
74 
75  // ArgLess: Index comparison between MappingItems
76 
77  template<typename A, typename B>
78  struct ArgLess
79  {
80  typedef boost::true_type type;
81  };
82 
83  template<typename A, int I, typename B>
84  struct ArgLess<A, MappingItem<I, B> >
85  {
86  typedef boost::true_type type;
87  };
88 
89  template<typename A, int I, typename B>
90  struct ArgLess<MappingItem<I, B>, A>
91  {
92  typedef boost::false_type type;
93  };
94 
95  template<int I1, typename V1, int I2, typename V2>
96  struct ArgLess<MappingItem<I1, V1>, MappingItem<I2, V2> >
97  {
98  typedef typename boost::mpl::less<boost::mpl::long_<I1>, boost::mpl::long_<I2> >::type type;
99  };
100 
101 
102  // MapItemIndexIs: By-index MappingItem find helper
103 
104  template<typename A, typename B>
105  struct MapItemIndexIs
106  {
107  typedef typename boost::false_type type;
108  };
109 
110  template<typename T, int B>
111  struct MapItemIndexIs<MappingItem<B, T>, boost::mpl::long_<B> >
112  {
113  typedef typename boost::true_type type;
114  };
115 
116 
117  // ReorderMapping: Reorder a sequence of MappingItems by their id
118 
119  template<int I, typename Map>
121  {
122  typedef typename boost::mpl::push_back<
123  typename ReorderMapping<I-1, Map>::type,
124  typename boost::mpl::deref<typename boost::mpl::find_if<
125  Map,
126  MapItemIndexIs<boost::mpl::_1, boost::mpl::long_<I> >
127  >::type
129  };
130 
131  template<typename Map>
132  struct ReorderMapping<1, Map>
133  {
134  typedef boost::mpl::vector<
135  typename boost::mpl::deref<typename boost::mpl::find_if<
136  Map,
137  MapItemIndexIs<boost::mpl::_1, boost::mpl::long_<1> >
139  };
140 
141  template<typename Map>
142  struct ReorderMapping<0, Map>
143  {
144  typedef boost::mpl::vector<> type;
145  };
146 
147 
148  // MappingToType: get type of MappingItem, or boost::any
149 
150  template<typename T>
152  {
153  typedef boost::any type;
154  };
155 
156  template<typename T, int I>
157  struct MappingToType<MappingItem<I, T> >
158  {
159  typedef T type;
160  };
161 
162 
163  // MappingBuilder: Invoke ArgResolver on all elements of a sequence
164 
165  template<int idx, typename F, typename V>
167  {
168  typedef typename boost::mpl::push_back<
169  typename MappingBuilder<idx - 1, F, V>::type,
172  };
173 
174  template<typename F, typename V>
175  struct MappingBuilder<0, F, V>
176  {
177  typedef typename boost::mpl::vector<
179  > type;
180  };
181 
182  template<typename F, typename S>
184  {
187  };
188 
189  template<typename T> struct BilistToSeq
190  {
191  typedef boost::mpl::vector<> type;
192  };
193 
194  template<typename P1>
195  struct BilistToSeq<boost::_bi::list1<P1> >
196  {
197  typedef typename boost::mpl::vector<P1> type;
198  };
199 
200  template<typename P1, typename P2>
201  struct BilistToSeq<boost::_bi::list2<P1, P2> >
202  {
203  typedef typename boost::mpl::vector<P1, P2> type;
204  };
205 
206  template<typename P1, typename P2, typename P3>
207  struct BilistToSeq<boost::_bi::list3<P1, P2, P3> >
208  {
209  typedef typename boost::mpl::vector<P1, P2, P3> type;
210  };
211 
212  template<typename P1, typename P2, typename P3, typename P4>
213  struct BilistToSeq<boost::_bi::list4<P1, P2, P3, P4> >
214  {
215  typedef typename boost::mpl::vector<P1, P2, P3, P4> type;
216  };
217 
218  template<typename P1, typename P2, typename P3, typename P4, typename P5>
219  struct BilistToSeq<boost::_bi::list5<P1, P2, P3, P4, P5> >
220  {
221  typedef typename boost::mpl::vector<P1, P2, P3, P4, P5> type;
222  };
223 
224  template<typename F, typename BL>
226  {
227  typedef typename BilistToSeq<BL>::type BLSeq;
229  // Mapping is a vector of nothing or pair<index, type>
230  // Get max value
231  typedef typename boost::mpl::deref<typename boost::mpl::max_element<Mapping, ArgLess<boost::mpl::_1, boost::mpl::_2> >::type>::type MaxArg;
232  // Reorder it
234  //typedef typename Reorder<Mapping, MaxArg>::type Reordered;
235  // Replace MappingItem with the type, and void with any
236  typedef typename boost::mpl::transform<Reordered, MappingToType<boost::mpl::_1> >::type type;
237  };
238  }
239 
240  template<typename T> struct boost_bind_result_type {};
241  template<typename R, typename A, typename B>
242  struct boost_bind_result_type<boost::_bi::bind_t<R, A, B> >
243  {
244  typedef R type;
245  };
246 
247  template<typename T> struct boost_bind_parameter_types {};
248  template<typename R, typename F, typename B>
249  struct boost_bind_parameter_types<boost::_bi::bind_t<R, F, B> >
250  {
251  typedef typename detail::parameter_types<F, B>::type type;
252  };
253 
257  template<typename T> struct boost_bind_function_type
258  {
259  typedef typename boost::function_types::function_type<
260  typename boost::mpl::push_front<
263  >::type
265  typedef typename boost::function_types::function_pointer<
266  typename boost::mpl::push_front<
269  >::type
271  };
272 }
273 
274 #endif // _QITYPE_DETAILS_BINDTYPE_HXX_
boost::mpl::vector< typename ArgResolver< F, 0, typename boost::mpl::at_c< V, 0 >::type >::type > type
Definition: bindtype.hxx:179
boost::function_types::function_pointer< typename boost::mpl::push_front< typename boost_bind_parameter_types< T >::type, typename boost_bind_result_type< T >::type >::type >::type pointer_type
Definition: bindtype.hxx:270
boost::function_types::function_type< typename boost::mpl::push_front< typename boost_bind_parameter_types< T >::type, typename boost_bind_result_type< T >::type >::type >::type type
Definition: bindtype.hxx:264
boost::mpl::vector< typename boost::mpl::deref< typename boost::mpl::find_if< Map, MapItemIndexIs< boost::mpl::_1, boost::mpl::long_< 1 > > >::type >::type > type
Definition: bindtype.hxx:138
BilistToSeq< BL >::type BLSeq
Definition: bindtype.hxx:227
boost::mpl::push_back< typename ReorderMapping< I-1, Map >::type, typename boost::mpl::deref< typename boost::mpl::find_if< Map, MapItemIndexIs< boost::mpl::_1, boost::mpl::long_< I > > >::type >::type >::type type
Definition: bindtype.hxx:128
static const long value
Definition: bindtype.hxx:39
boost::mpl::transform< Reordered, MappingToType< boost::mpl::_1 > >::type type
Definition: bindtype.hxx:236
boost::mpl::deref< typename boost::mpl::max_element< Mapping, ArgLess< boost::mpl::_1, boost::mpl::_2 > >::type >::type MaxArg
Definition: bindtype.hxx:231
ReorderMapping< IntFromMappingItem< MaxArg >::value, Mapping >::type Reordered
Definition: bindtype.hxx:233
parameter_types_from_bilist_seq< F, BLSeq >::type Mapping
Definition: bindtype.hxx:228
boost::mpl::push_back< typename MappingBuilder< idx-1, F, V >::type, typename ArgResolver< F, idx, typename boost::mpl::at_c< V, idx >::type >::type >::type type
Definition: bindtype.hxx:171
MappingBuilder< boost::mpl::size< S >::type::value-1, F, S >::type type
Definition: bindtype.hxx:186