00001
00002 #ifndef _INSTIGATE_OPEN_SOURCE_INTERNAL_HEADER_IN_CONCEPT
00003 #error This is an internal header file used to implement Instigate STL.\
00004 It should never be included directly by a program.
00005 #endif
00006
00007 #ifndef INSTIGATE_STL_TERNARY_FUNCTION
00008 #define INSTIGATE_STL_TERNARY_FUNCTION
00009
00059
00060
00061
00062
00063
00064
00065
00066 namespace instigate {
00067 namespace stl {
00100 namespace ternary_function{
00101 template <typename T>
00102 struct interface;
00103 template <typename R, typename A, typename B,
00104 typename C>
00105 struct interface<R (*) (A, B, C)>;
00106 template <typename R, typename A, typename B,
00107 typename C>
00108 struct interface <R (A::*) (B, C)>;
00109 template <typename R, typename A, typename B,
00110 typename C>
00111 struct interface <R (A::*) (B, C) const>;
00112 template <typename T> struct requirements;
00113 }
00114 }
00115 }
00116
00117
00122 template <typename TF>
00123 struct instigate::stl::ternary_function::interface
00124 : instigate::generic::assignable::interface<TF>
00125 {
00127 typedef typename TF::first_argument_type first_argument_type;
00128
00130 typedef typename TF::second_argument_type second_argument_type;
00131
00133 typedef typename TF::third_argument_type third_argument_type;
00134
00136 typedef typename TF::result_type result_type;
00137
00147 static result_type invoke(const TF& f,
00148 first_argument_type a1,
00149 second_argument_type a2,
00150 third_argument_type a3)
00151 {
00152 return f(a1, a2, a3);
00153 }
00154
00155 };
00156
00160 template <typename R, typename A, typename B, typename C>
00161 struct instigate::stl::ternary_function::interface<R (*) (A, B, C)> :
00162 instigate::generic::assignable::interface<R (*) (A, B, C)>
00163 {
00165 typedef A first_argument_type;
00166
00168 typedef B second_argument_type;
00169
00171 typedef C third_argument_type;
00172
00174 typedef R result_type;
00175
00185 static result_type invoke(R (*f)(A, B, C), A a1, B a2, C a3)
00186 {
00187 return f(a1, a2, a3);
00188 }
00189 };
00190
00194 template <typename R, typename A, typename B, typename C>
00195 struct instigate::stl::ternary_function::interface <R (A::*) (B, C)>
00196 : instigate::generic::assignable::interface<R (A::*) (B, C)>
00197 {
00199 typedef A* first_argument_type;
00200
00202 typedef B second_argument_type;
00203
00205 typedef C third_argument_type;
00206
00208 typedef R result_type;
00209
00221 static result_type invoke(R (A::*f)(B, C), A* a1, B a2, C a3)
00222 {
00223 assert(a1 != 0);
00224 return (a1->*f)(a2, a3);
00225 }
00226 };
00227
00232 template <typename R, typename A, typename B, typename C>
00233 struct instigate::stl::ternary_function::interface <R (A::*) (B, C) const>
00234 : instigate::generic::assignable::interface<R (A::*) (B, C) const>
00235 {
00237 typedef const A* first_argument_type;
00238
00240 typedef B second_argument_type;
00241
00243 typedef C third_argument_type;
00244
00246 typedef R result_type;
00247
00259 static result_type
00260 invoke(R (A::*f)(B, C) const, const A* a1, B a2, C a3)
00261 {
00262 assert(a1 != 0);
00263 return (a1->*f)(a2, a3);
00264 }
00265 };
00266
00273 template <typename T>
00274 struct instigate::stl::ternary_function::requirements
00275 : instigate::generic::assignable::interface<T>
00276 {
00281 static void require_nested_typename_first_argument_type()
00282 {
00283 namespace TF = instigate::stl::ternary_function;
00284 typedef TF::interface<T> I;
00285 typedef typename I::first_argument_type A;
00286 }
00287
00292 static void require_nested_typename_second_argument_type()
00293 {
00294 namespace TF = instigate::stl::ternary_function;
00295 typedef TF::interface<T> I;
00296 typedef typename I::second_argument_type B;
00297 }
00298
00303 static void require_nested_typename_third_argument_type()
00304 {
00305 namespace TF = instigate::stl::ternary_function;
00306 typedef TF::interface<T> I;
00307 typedef typename I::third_argument_type C;
00308 }
00309
00314 static void require_nested_typename_result_type()
00315 {
00316 namespace TF = instigate::stl::ternary_function;
00317 typedef TF::interface<T> I;
00318 typedef typename I::result_type R;
00319 }
00320
00325 static void require_method_invoke()
00326 {
00327 typedef instigate::stl::ternary_function::interface<T> I;
00328 (void)I::invoke;
00329 }
00330
00335 typename instigate::stl::ternary_function::interface<T>::
00336 result_type helper(const T& f,
00337 typename instigate::stl::ternary_function::
00338 interface<T>::first_argument_type a,
00339 typename instigate::stl::ternary_function::
00340 interface<T>::second_argument_type b,
00341 typename instigate::stl::ternary_function::
00342 interface<T>::third_argument_type c)
00343 {
00344 namespace TF = instigate::stl::ternary_function;
00345 typedef TF::interface<T> I;
00346 return I::invoke(f, a, b, c);
00347 }
00348
00353 static void check_signature_of_the_invoke()
00354 {
00355 (void)&requirements<T>::helper;
00356 }
00357
00362 requirements()
00363 {
00364 (void)require_nested_typename_first_argument_type;
00365 (void)require_nested_typename_second_argument_type;
00366 (void)require_nested_typename_third_argument_type;
00367 (void)require_nested_typename_result_type;
00368 (void)require_method_invoke;
00369 (void)check_signature_of_the_invoke;
00370 }
00371
00372 };
00373
00374
00375
00376 #endif // INSTIGATE_STL_TERNARY_FUNCTION