]>
Commit | Line | Data |
---|---|---|
7c673cae FG |
1 | // Boost Lambda Library - operator_lambda_func_base.hpp ----------------- |
2 | // | |
3 | // Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi) | |
4 | // | |
5 | // Distributed under the Boost Software License, Version 1.0. (See | |
6 | // accompanying file LICENSE_1_0.txt or copy at | |
7 | // http://www.boost.org/LICENSE_1_0.txt) | |
8 | // | |
9 | // For more information, see www.boost.org | |
10 | ||
11 | // ------------------------------------------------------------ | |
12 | ||
13 | #ifndef BOOST_LAMBDA_OPERATOR_LAMBDA_FUNC_BASE_HPP | |
14 | #define BOOST_LAMBDA_OPERATOR_LAMBDA_FUNC_BASE_HPP | |
15 | ||
16 | namespace boost { | |
17 | namespace lambda { | |
18 | ||
19 | ||
20 | // These operators cannot be implemented as apply functions of action | |
21 | // templates | |
22 | ||
23 | ||
24 | // Specialization for comma. | |
25 | template<class Args> | |
26 | class lambda_functor_base<other_action<comma_action>, Args> { | |
27 | public: | |
28 | Args args; | |
29 | public: | |
30 | explicit lambda_functor_base(const Args& a) : args(a) {} | |
31 | ||
32 | template<class RET, CALL_TEMPLATE_ARGS> | |
33 | RET call(CALL_FORMAL_ARGS) const { | |
34 | return detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS), | |
35 | detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS); | |
36 | } | |
37 | ||
38 | ||
39 | template<class SigArgs> struct sig { | |
40 | private: | |
41 | typedef typename | |
42 | detail::deduce_argument_types<Args, SigArgs>::type rets_t; | |
43 | public: | |
44 | typedef typename return_type_2_comma< // comma needs special handling | |
45 | typename detail::element_or_null<0, rets_t>::type, | |
46 | typename detail::element_or_null<1, rets_t>::type | |
47 | >::type type; | |
48 | }; | |
49 | ||
50 | }; | |
51 | ||
52 | namespace detail { | |
53 | ||
54 | // helper traits to make the expression shorter, takes binary action | |
55 | // bound argument tuple, open argument tuple and gives the return type | |
56 | ||
57 | template<class Action, class Bound, class Open> class binary_rt { | |
58 | private: | |
59 | typedef typename | |
60 | detail::deduce_argument_types<Bound, Open>::type rets_t; | |
61 | public: | |
62 | typedef typename return_type_2_prot< | |
63 | Action, | |
64 | typename detail::element_or_null<0, rets_t>::type, | |
65 | typename detail::element_or_null<1, rets_t>::type | |
66 | >::type type; | |
67 | }; | |
68 | ||
69 | ||
70 | // same for unary actions | |
71 | template<class Action, class Bound, class Open> class unary_rt { | |
72 | private: | |
73 | typedef typename | |
74 | detail::deduce_argument_types<Bound, Open>::type rets_t; | |
75 | public: | |
76 | typedef typename return_type_1_prot< | |
77 | Action, | |
78 | typename detail::element_or_null<0, rets_t>::type | |
79 | >::type type; | |
80 | }; | |
81 | ||
82 | ||
83 | } // end detail | |
84 | ||
85 | // Specialization for logical and (to preserve shortcircuiting) | |
86 | // this could be done with a macro as the others, code used to be different | |
87 | template<class Args> | |
88 | class lambda_functor_base<logical_action<and_action>, Args> { | |
89 | public: | |
90 | Args args; | |
91 | public: | |
92 | explicit lambda_functor_base(const Args& a) : args(a) {} | |
93 | ||
94 | template<class RET, CALL_TEMPLATE_ARGS> | |
95 | RET call(CALL_FORMAL_ARGS) const { | |
96 | return detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS) && | |
97 | detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS); | |
98 | } | |
99 | template<class SigArgs> struct sig { | |
100 | typedef typename | |
101 | detail::binary_rt<logical_action<and_action>, Args, SigArgs>::type type; | |
102 | }; | |
103 | }; | |
104 | ||
105 | // Specialization for logical or (to preserve shortcircuiting) | |
106 | // this could be done with a macro as the others, code used to be different | |
107 | template<class Args> | |
108 | class lambda_functor_base<logical_action< or_action>, Args> { | |
109 | public: | |
110 | Args args; | |
111 | public: | |
112 | explicit lambda_functor_base(const Args& a) : args(a) {} | |
113 | ||
114 | template<class RET, CALL_TEMPLATE_ARGS> | |
115 | RET call(CALL_FORMAL_ARGS) const { | |
116 | return detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS) || | |
117 | detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS); | |
118 | } | |
119 | ||
120 | template<class SigArgs> struct sig { | |
121 | typedef typename | |
122 | detail::binary_rt<logical_action<or_action>, Args, SigArgs>::type type; | |
123 | }; | |
124 | }; | |
125 | ||
126 | // Specialization for subscript | |
127 | template<class Args> | |
128 | class lambda_functor_base<other_action<subscript_action>, Args> { | |
129 | public: | |
130 | Args args; | |
131 | public: | |
132 | explicit lambda_functor_base(const Args& a) : args(a) {} | |
133 | ||
134 | template<class RET, CALL_TEMPLATE_ARGS> | |
135 | RET call(CALL_FORMAL_ARGS) const { | |
136 | return detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS) | |
137 | [detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS)]; | |
138 | } | |
139 | ||
140 | template<class SigArgs> struct sig { | |
141 | typedef typename | |
142 | detail::binary_rt<other_action<subscript_action>, Args, SigArgs>::type | |
143 | type; | |
144 | }; | |
145 | }; | |
146 | ||
147 | ||
148 | #define BOOST_LAMBDA_BINARY_ACTION(SYMBOL, ACTION_CLASS) \ | |
149 | template<class Args> \ | |
150 | class lambda_functor_base<ACTION_CLASS, Args> { \ | |
151 | public: \ | |
152 | Args args; \ | |
153 | public: \ | |
154 | explicit lambda_functor_base(const Args& a) : args(a) {} \ | |
155 | \ | |
156 | template<class RET, CALL_TEMPLATE_ARGS> \ | |
157 | RET call(CALL_FORMAL_ARGS) const { \ | |
158 | return detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS) \ | |
159 | SYMBOL \ | |
160 | detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS); \ | |
161 | } \ | |
162 | template<class SigArgs> struct sig { \ | |
163 | typedef typename \ | |
164 | detail::binary_rt<ACTION_CLASS, Args, SigArgs>::type type; \ | |
165 | }; \ | |
166 | }; | |
167 | ||
168 | #define BOOST_LAMBDA_PREFIX_UNARY_ACTION(SYMBOL, ACTION_CLASS) \ | |
169 | template<class Args> \ | |
170 | class lambda_functor_base<ACTION_CLASS, Args> { \ | |
171 | public: \ | |
172 | Args args; \ | |
173 | public: \ | |
174 | explicit lambda_functor_base(const Args& a) : args(a) {} \ | |
175 | \ | |
176 | template<class RET, CALL_TEMPLATE_ARGS> \ | |
177 | RET call(CALL_FORMAL_ARGS) const { \ | |
178 | return SYMBOL \ | |
179 | detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS); \ | |
180 | } \ | |
181 | template<class SigArgs> struct sig { \ | |
182 | typedef typename \ | |
183 | detail::unary_rt<ACTION_CLASS, Args, SigArgs>::type type; \ | |
184 | }; \ | |
185 | }; | |
186 | ||
187 | #define BOOST_LAMBDA_POSTFIX_UNARY_ACTION(SYMBOL, ACTION_CLASS) \ | |
188 | template<class Args> \ | |
189 | class lambda_functor_base<ACTION_CLASS, Args> { \ | |
190 | public: \ | |
191 | Args args; \ | |
192 | public: \ | |
193 | explicit lambda_functor_base(const Args& a) : args(a) {} \ | |
194 | \ | |
195 | template<class RET, CALL_TEMPLATE_ARGS> \ | |
196 | RET call(CALL_FORMAL_ARGS) const { \ | |
197 | return \ | |
198 | detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS) SYMBOL; \ | |
199 | } \ | |
200 | template<class SigArgs> struct sig { \ | |
201 | typedef typename \ | |
202 | detail::unary_rt<ACTION_CLASS, Args, SigArgs>::type type; \ | |
203 | }; \ | |
204 | }; | |
205 | ||
206 | BOOST_LAMBDA_BINARY_ACTION(+,arithmetic_action<plus_action>) | |
207 | BOOST_LAMBDA_BINARY_ACTION(-,arithmetic_action<minus_action>) | |
208 | BOOST_LAMBDA_BINARY_ACTION(*,arithmetic_action<multiply_action>) | |
209 | BOOST_LAMBDA_BINARY_ACTION(/,arithmetic_action<divide_action>) | |
210 | BOOST_LAMBDA_BINARY_ACTION(%,arithmetic_action<remainder_action>) | |
211 | ||
212 | BOOST_LAMBDA_BINARY_ACTION(<<,bitwise_action<leftshift_action>) | |
213 | BOOST_LAMBDA_BINARY_ACTION(>>,bitwise_action<rightshift_action>) | |
214 | BOOST_LAMBDA_BINARY_ACTION(&,bitwise_action<and_action>) | |
215 | BOOST_LAMBDA_BINARY_ACTION(|,bitwise_action<or_action>) | |
216 | BOOST_LAMBDA_BINARY_ACTION(^,bitwise_action<xor_action>) | |
217 | ||
218 | BOOST_LAMBDA_BINARY_ACTION(<,relational_action<less_action>) | |
219 | BOOST_LAMBDA_BINARY_ACTION(>,relational_action<greater_action>) | |
220 | BOOST_LAMBDA_BINARY_ACTION(<=,relational_action<lessorequal_action>) | |
221 | BOOST_LAMBDA_BINARY_ACTION(>=,relational_action<greaterorequal_action>) | |
222 | BOOST_LAMBDA_BINARY_ACTION(==,relational_action<equal_action>) | |
223 | BOOST_LAMBDA_BINARY_ACTION(!=,relational_action<notequal_action>) | |
224 | ||
225 | BOOST_LAMBDA_BINARY_ACTION(+=,arithmetic_assignment_action<plus_action>) | |
226 | BOOST_LAMBDA_BINARY_ACTION(-=,arithmetic_assignment_action<minus_action>) | |
227 | BOOST_LAMBDA_BINARY_ACTION(*=,arithmetic_assignment_action<multiply_action>) | |
228 | BOOST_LAMBDA_BINARY_ACTION(/=,arithmetic_assignment_action<divide_action>) | |
229 | BOOST_LAMBDA_BINARY_ACTION(%=,arithmetic_assignment_action<remainder_action>) | |
230 | ||
231 | BOOST_LAMBDA_BINARY_ACTION(<<=,bitwise_assignment_action<leftshift_action>) | |
232 | BOOST_LAMBDA_BINARY_ACTION(>>=,bitwise_assignment_action<rightshift_action>) | |
233 | BOOST_LAMBDA_BINARY_ACTION(&=,bitwise_assignment_action<and_action>) | |
234 | BOOST_LAMBDA_BINARY_ACTION(|=,bitwise_assignment_action<or_action>) | |
235 | BOOST_LAMBDA_BINARY_ACTION(^=,bitwise_assignment_action<xor_action>) | |
236 | ||
237 | BOOST_LAMBDA_BINARY_ACTION(=,other_action< assignment_action>) | |
238 | ||
239 | ||
240 | BOOST_LAMBDA_PREFIX_UNARY_ACTION(+, unary_arithmetic_action<plus_action>) | |
241 | BOOST_LAMBDA_PREFIX_UNARY_ACTION(-, unary_arithmetic_action<minus_action>) | |
242 | BOOST_LAMBDA_PREFIX_UNARY_ACTION(~, bitwise_action<not_action>) | |
243 | BOOST_LAMBDA_PREFIX_UNARY_ACTION(!, logical_action<not_action>) | |
244 | BOOST_LAMBDA_PREFIX_UNARY_ACTION(++, pre_increment_decrement_action<increment_action>) | |
245 | BOOST_LAMBDA_PREFIX_UNARY_ACTION(--, pre_increment_decrement_action<decrement_action>) | |
246 | ||
247 | BOOST_LAMBDA_PREFIX_UNARY_ACTION(&,other_action<addressof_action>) | |
248 | BOOST_LAMBDA_PREFIX_UNARY_ACTION(*,other_action<contentsof_action>) | |
249 | ||
250 | BOOST_LAMBDA_POSTFIX_UNARY_ACTION(++, post_increment_decrement_action<increment_action>) | |
251 | BOOST_LAMBDA_POSTFIX_UNARY_ACTION(--, post_increment_decrement_action<decrement_action>) | |
252 | ||
253 | ||
254 | #undef BOOST_LAMBDA_POSTFIX_UNARY_ACTION | |
255 | #undef BOOST_LAMBDA_PREFIX_UNARY_ACTION | |
256 | #undef BOOST_LAMBDA_BINARY_ACTION | |
257 | ||
258 | } // namespace lambda | |
259 | } // namespace boost | |
260 | ||
261 | #endif | |
262 | ||
263 | ||
264 | ||
265 | ||
266 | ||
267 | ||
268 | ||
269 | ||
270 | ||
271 |