__functional_base_03 6.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224
  1. // -*- C++ -*-
  2. //===----------------------------------------------------------------------===//
  3. //
  4. // The LLVM Compiler Infrastructure
  5. //
  6. // This file is dual licensed under the MIT and the University of Illinois Open
  7. // Source Licenses. See LICENSE.TXT for details.
  8. //
  9. //===----------------------------------------------------------------------===//
  10. #ifndef _LIBCPP_FUNCTIONAL_BASE_03
  11. #define _LIBCPP_FUNCTIONAL_BASE_03
  12. // manual variadic expansion for <functional>
  13. // __invoke
  14. template <class _Ret, class _T1, bool _IsFunc, bool _IsBase>
  15. struct __enable_invoke_imp;
  16. template <class _Ret, class _T1>
  17. struct __enable_invoke_imp<_Ret, _T1, true, true> {
  18. typedef _Ret _Bullet1;
  19. typedef _Bullet1 type;
  20. };
  21. template <class _Ret, class _T1>
  22. struct __enable_invoke_imp<_Ret, _T1, true, false> {
  23. typedef _Ret _Bullet2;
  24. typedef _Bullet2 type;
  25. };
  26. template <class _Ret, class _T1>
  27. struct __enable_invoke_imp<_Ret, _T1, false, true> {
  28. typedef typename add_lvalue_reference<
  29. typename __apply_cv<_T1, _Ret>::type
  30. >::type _Bullet3;
  31. typedef _Bullet3 type;
  32. };
  33. template <class _Ret, class _T1>
  34. struct __enable_invoke_imp<_Ret, _T1, false, false> {
  35. typedef typename add_lvalue_reference<
  36. typename __apply_cv<decltype(*_VSTD::declval<_T1>()), _Ret>::type
  37. >::type _Bullet4;
  38. typedef _Bullet4 type;
  39. };
  40. template <class _Ret, class _T1>
  41. struct __enable_invoke_imp<_Ret, _T1*, false, false> {
  42. typedef typename add_lvalue_reference<
  43. typename __apply_cv<_T1, _Ret>::type
  44. >::type _Bullet4;
  45. typedef _Bullet4 type;
  46. };
  47. template <class _Fn, class _T1,
  48. class _Traits = __member_pointer_traits<_Fn>,
  49. class _Ret = typename _Traits::_ReturnType,
  50. class _Class = typename _Traits::_ClassType>
  51. struct __enable_invoke : __enable_invoke_imp<
  52. _Ret, _T1,
  53. is_member_function_pointer<_Fn>::value,
  54. is_base_of<_Class, typename remove_reference<_T1>::type>::value>
  55. {
  56. };
  57. __nat __invoke(__any, ...);
  58. // first bullet
  59. template <class _Fn, class _T1>
  60. inline _LIBCPP_INLINE_VISIBILITY
  61. typename __enable_invoke<_Fn, _T1>::_Bullet1
  62. __invoke(_Fn __f, _T1& __t1) {
  63. return (__t1.*__f)();
  64. }
  65. template <class _Fn, class _T1, class _A0>
  66. inline _LIBCPP_INLINE_VISIBILITY
  67. typename __enable_invoke<_Fn, _T1>::_Bullet1
  68. __invoke(_Fn __f, _T1& __t1, _A0& __a0) {
  69. return (__t1.*__f)(__a0);
  70. }
  71. template <class _Fn, class _T1, class _A0, class _A1>
  72. inline _LIBCPP_INLINE_VISIBILITY
  73. typename __enable_invoke<_Fn, _T1>::_Bullet1
  74. __invoke(_Fn __f, _T1& __t1, _A0& __a0, _A1& __a1) {
  75. return (__t1.*__f)(__a0, __a1);
  76. }
  77. template <class _Fn, class _T1, class _A0, class _A1, class _A2>
  78. inline _LIBCPP_INLINE_VISIBILITY
  79. typename __enable_invoke<_Fn, _T1>::_Bullet1
  80. __invoke(_Fn __f, _T1& __t1, _A0& __a0, _A1& __a1, _A2& __a2) {
  81. return (__t1.*__f)(__a0, __a1, __a2);
  82. }
  83. template <class _Fn, class _T1>
  84. inline _LIBCPP_INLINE_VISIBILITY
  85. typename __enable_invoke<_Fn, _T1>::_Bullet2
  86. __invoke(_Fn __f, _T1& __t1) {
  87. return ((*__t1).*__f)();
  88. }
  89. template <class _Fn, class _T1, class _A0>
  90. inline _LIBCPP_INLINE_VISIBILITY
  91. typename __enable_invoke<_Fn, _T1>::_Bullet2
  92. __invoke(_Fn __f, _T1& __t1, _A0& __a0) {
  93. return ((*__t1).*__f)(__a0);
  94. }
  95. template <class _Fn, class _T1, class _A0, class _A1>
  96. inline _LIBCPP_INLINE_VISIBILITY
  97. typename __enable_invoke<_Fn, _T1>::_Bullet2
  98. __invoke(_Fn __f, _T1& __t1, _A0& __a0, _A1& __a1) {
  99. return ((*__t1).*__f)(__a0, __a1);
  100. }
  101. template <class _Fn, class _T1, class _A0, class _A1, class _A2>
  102. inline _LIBCPP_INLINE_VISIBILITY
  103. typename __enable_invoke<_Fn, _T1>::_Bullet2
  104. __invoke(_Fn __f, _T1& __t1, _A0& __a0, _A1& __a1, _A2& __a2) {
  105. return ((*__t1).*__f)(__a0, __a1, __a2);
  106. }
  107. template <class _Fn, class _T1>
  108. inline _LIBCPP_INLINE_VISIBILITY
  109. typename __enable_invoke<_Fn, _T1>::_Bullet3
  110. __invoke(_Fn __f, _T1& __t1) {
  111. return __t1.*__f;
  112. }
  113. template <class _Fn, class _T1>
  114. inline _LIBCPP_INLINE_VISIBILITY
  115. typename __enable_invoke<_Fn, _T1>::_Bullet4
  116. __invoke(_Fn __f, _T1& __t1) {
  117. return (*__t1).*__f;
  118. }
  119. // fifth bullet
  120. template <class _Fp>
  121. inline _LIBCPP_INLINE_VISIBILITY
  122. decltype(_VSTD::declval<_Fp&>()())
  123. __invoke(_Fp& __f)
  124. {
  125. return __f();
  126. }
  127. template <class _Fp, class _A0>
  128. inline _LIBCPP_INLINE_VISIBILITY
  129. decltype(_VSTD::declval<_Fp&>()(_VSTD::declval<_A0&>()))
  130. __invoke(_Fp& __f, _A0& __a0)
  131. {
  132. return __f(__a0);
  133. }
  134. template <class _Fp, class _A0, class _A1>
  135. inline _LIBCPP_INLINE_VISIBILITY
  136. decltype(_VSTD::declval<_Fp&>()(_VSTD::declval<_A0&>(), _VSTD::declval<_A1&>()))
  137. __invoke(_Fp& __f, _A0& __a0, _A1& __a1)
  138. {
  139. return __f(__a0, __a1);
  140. }
  141. template <class _Fp, class _A0, class _A1, class _A2>
  142. inline _LIBCPP_INLINE_VISIBILITY
  143. decltype(_VSTD::declval<_Fp&>()(_VSTD::declval<_A0&>(), _VSTD::declval<_A1&>(), _VSTD::declval<_A2&>()))
  144. __invoke(_Fp& __f, _A0& __a0, _A1& __a1, _A2& __a2)
  145. {
  146. return __f(__a0, __a1, __a2);
  147. }
  148. template <class _Fp, bool = __has_result_type<__weak_result_type<_Fp> >::value>
  149. struct __invoke_return
  150. {
  151. typedef typename __weak_result_type<_Fp>::result_type type;
  152. };
  153. template <class _Fp>
  154. struct __invoke_return<_Fp, false>
  155. {
  156. typedef decltype(__invoke(_VSTD::declval<_Fp&>())) type;
  157. };
  158. template <class _Tp, class _A0>
  159. struct __invoke_return0
  160. {
  161. typedef decltype(__invoke(_VSTD::declval<_Tp&>(), _VSTD::declval<_A0&>())) type;
  162. };
  163. template <class _Rp, class _Tp, class _A0>
  164. struct __invoke_return0<_Rp _Tp::*, _A0>
  165. {
  166. typedef typename __enable_invoke<_Rp _Tp::*, _A0>::type type;
  167. };
  168. template <class _Tp, class _A0, class _A1>
  169. struct __invoke_return1
  170. {
  171. typedef decltype(__invoke(_VSTD::declval<_Tp&>(), _VSTD::declval<_A0&>(),
  172. _VSTD::declval<_A1&>())) type;
  173. };
  174. template <class _Rp, class _Class, class _A0, class _A1>
  175. struct __invoke_return1<_Rp _Class::*, _A0, _A1> {
  176. typedef typename __enable_invoke<_Rp _Class::*, _A0>::type type;
  177. };
  178. template <class _Tp, class _A0, class _A1, class _A2>
  179. struct __invoke_return2
  180. {
  181. typedef decltype(__invoke(_VSTD::declval<_Tp&>(), _VSTD::declval<_A0&>(),
  182. _VSTD::declval<_A1&>(),
  183. _VSTD::declval<_A2&>())) type;
  184. };
  185. template <class _Ret, class _Class, class _A0, class _A1, class _A2>
  186. struct __invoke_return2<_Ret _Class::*, _A0, _A1, _A2> {
  187. typedef typename __enable_invoke<_Ret _Class::*, _A0>::type type;
  188. };
  189. #endif // _LIBCPP_FUNCTIONAL_BASE_03