Skip to content

Commit 41efe9e

Browse files
committed
[libc++] Define an internal API for std::invoke and friends
1 parent 3535ea0 commit 41efe9e

File tree

17 files changed

+219
-63
lines changed

17 files changed

+219
-63
lines changed

libcxx/include/__algorithm/make_projected.h

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -37,16 +37,16 @@ struct _ProjectedPred {
3737
: __pred(__pred_arg), __proj(__proj_arg) {}
3838

3939
template <class _Tp>
40-
typename __invoke_of<_Pred&, decltype(std::__invoke(std::declval<_Proj&>(), std::declval<_Tp>()))>::type
41-
_LIBCPP_CONSTEXPR _LIBCPP_HIDE_FROM_ABI
42-
operator()(_Tp&& __v) const {
40+
__invoke_result_t<_Pred&, decltype(std::__invoke(std::declval<_Proj&>(), std::declval<_Tp>()))> _LIBCPP_CONSTEXPR
41+
_LIBCPP_HIDE_FROM_ABI
42+
operator()(_Tp&& __v) const {
4343
return std::__invoke(__pred, std::__invoke(__proj, std::forward<_Tp>(__v)));
4444
}
4545

4646
template <class _T1, class _T2>
47-
typename __invoke_of<_Pred&,
48-
decltype(std::__invoke(std::declval<_Proj&>(), std::declval<_T1>())),
49-
decltype(std::__invoke(std::declval<_Proj&>(), std::declval<_T2>()))>::type _LIBCPP_CONSTEXPR
47+
__invoke_result_t<_Pred&,
48+
decltype(std::__invoke(std::declval<_Proj&>(), std::declval<_T1>())),
49+
decltype(std::__invoke(std::declval<_Proj&>(), std::declval<_T2>()))> _LIBCPP_CONSTEXPR
5050
_LIBCPP_HIDE_FROM_ABI
5151
operator()(_T1&& __lhs, _T2&& __rhs) const {
5252
return std::__invoke(

libcxx/include/__functional/bind.h

Lines changed: 10 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -82,13 +82,13 @@ inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 _Tp& __mu(reference_w
8282
}
8383

8484
template <class _Ti, class... _Uj, size_t... _Indx>
85-
inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 typename __invoke_of<_Ti&, _Uj...>::type
85+
inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 __invoke_result_t<_Ti&, _Uj...>
8686
__mu_expand(_Ti& __ti, tuple<_Uj...>& __uj, __tuple_indices<_Indx...>) {
8787
return __ti(std::forward<_Uj>(std::get<_Indx>(__uj))...);
8888
}
8989

9090
template <class _Ti, class... _Uj, __enable_if_t<is_bind_expression<_Ti>::value, int> = 0>
91-
inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 typename __invoke_of<_Ti&, _Uj...>::type
91+
inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 __invoke_result_t<_Ti&, _Uj...>
9292
__mu(_Ti& __ti, tuple<_Uj...>& __uj) {
9393
typedef typename __make_tuple_indices<sizeof...(_Uj)>::type __indices;
9494
return std::__mu_expand(__ti, __uj, __indices());
@@ -130,12 +130,12 @@ struct __mu_return_invokable // false
130130

131131
template <class _Ti, class... _Uj>
132132
struct __mu_return_invokable<true, _Ti, _Uj...> {
133-
typedef typename __invoke_of<_Ti&, _Uj...>::type type;
133+
using type = __invoke_result_t<_Ti&, _Uj...>;
134134
};
135135

136136
template <class _Ti, class... _Uj>
137137
struct __mu_return_impl<_Ti, false, true, false, tuple<_Uj...> >
138-
: public __mu_return_invokable<__invokable<_Ti&, _Uj...>::value, _Ti, _Uj...> {};
138+
: public __mu_return_invokable<__is_invocable_v<_Ti&, _Uj...>, _Ti, _Uj...> {};
139139

140140
template <class _Ti, class _TupleUj>
141141
struct __mu_return_impl<_Ti, false, false, true, _TupleUj> {
@@ -168,25 +168,25 @@ struct __is_valid_bind_return {
168168

169169
template <class _Fp, class... _BoundArgs, class _TupleUj>
170170
struct __is_valid_bind_return<_Fp, tuple<_BoundArgs...>, _TupleUj> {
171-
static const bool value = __invokable<_Fp, typename __mu_return<_BoundArgs, _TupleUj>::type...>::value;
171+
static const bool value = __is_invocable_v<_Fp, typename __mu_return<_BoundArgs, _TupleUj>::type...>;
172172
};
173173

174174
template <class _Fp, class... _BoundArgs, class _TupleUj>
175175
struct __is_valid_bind_return<_Fp, const tuple<_BoundArgs...>, _TupleUj> {
176-
static const bool value = __invokable<_Fp, typename __mu_return<const _BoundArgs, _TupleUj>::type...>::value;
176+
static const bool value = __is_invocable_v<_Fp, typename __mu_return<const _BoundArgs, _TupleUj>::type...>;
177177
};
178178

179179
template <class _Fp, class _BoundArgs, class _TupleUj, bool = __is_valid_bind_return<_Fp, _BoundArgs, _TupleUj>::value>
180180
struct __bind_return;
181181

182182
template <class _Fp, class... _BoundArgs, class _TupleUj>
183183
struct __bind_return<_Fp, tuple<_BoundArgs...>, _TupleUj, true> {
184-
typedef typename __invoke_of< _Fp&, typename __mu_return< _BoundArgs, _TupleUj >::type... >::type type;
184+
using type = __invoke_result_t< _Fp&, typename __mu_return< _BoundArgs, _TupleUj >::type... >;
185185
};
186186

187187
template <class _Fp, class... _BoundArgs, class _TupleUj>
188188
struct __bind_return<_Fp, const tuple<_BoundArgs...>, _TupleUj, true> {
189-
typedef typename __invoke_of< _Fp&, typename __mu_return< const _BoundArgs, _TupleUj >::type... >::type type;
189+
using type = __invoke_result_t< _Fp&, typename __mu_return< const _BoundArgs, _TupleUj >::type... >;
190190
};
191191

192192
template <class _Fp, class _BoundArgs, size_t... _Indx, class _Args>
@@ -256,8 +256,7 @@ class __bind_r : public __bind<_Fp, _BoundArgs...> {
256256
is_void<_Rp>::value,
257257
int> = 0>
258258
_LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 result_type operator()(_Args&&... __args) {
259-
typedef __invoke_void_return_wrapper<_Rp> _Invoker;
260-
return _Invoker::__call(static_cast<base&>(*this), std::forward<_Args>(__args)...);
259+
return std::__invoke_r<_Rp>(static_cast<base&>(*this), std::forward<_Args>(__args)...);
261260
}
262261

263262
template <class... _Args,
@@ -266,8 +265,7 @@ class __bind_r : public __bind<_Fp, _BoundArgs...> {
266265
is_void<_Rp>::value,
267266
int> = 0>
268267
_LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 result_type operator()(_Args&&... __args) const {
269-
typedef __invoke_void_return_wrapper<_Rp> _Invoker;
270-
return _Invoker::__call(static_cast<base const&>(*this), std::forward<_Args>(__args)...);
268+
return std::__invoke_r<_Rp>(static_cast<base const&>(*this), std::forward<_Args>(__args)...);
271269
}
272270
};
273271

libcxx/include/__functional/function.h

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -166,8 +166,7 @@ class __alloc_func<_Fp, _Ap, _Rp(_ArgTypes...)> {
166166
: __func_(std::move(__f)), __alloc_(std::move(__a)) {}
167167

168168
_LIBCPP_HIDE_FROM_ABI _Rp operator()(_ArgTypes&&... __arg) {
169-
typedef __invoke_void_return_wrapper<_Rp> _Invoker;
170-
return _Invoker::__call(__func_, std::forward<_ArgTypes>(__arg)...);
169+
return std::__invoke_r<_Rp>(__func_, std::forward<_ArgTypes>(__arg)...);
171170
}
172171

173172
_LIBCPP_HIDE_FROM_ABI __alloc_func* __clone() const {
@@ -208,8 +207,7 @@ class __default_alloc_func<_Fp, _Rp(_ArgTypes...)> {
208207
_LIBCPP_HIDE_FROM_ABI explicit __default_alloc_func(const _Target& __f) : __f_(__f) {}
209208

210209
_LIBCPP_HIDE_FROM_ABI _Rp operator()(_ArgTypes&&... __arg) {
211-
typedef __invoke_void_return_wrapper<_Rp> _Invoker;
212-
return _Invoker::__call(__f_, std::forward<_ArgTypes>(__arg)...);
210+
return std::__invoke_r<_Rp>(__f_, std::forward<_ArgTypes>(__arg)...);
213211
}
214212

215213
_LIBCPP_HIDE_FROM_ABI __default_alloc_func* __clone() const {
@@ -835,12 +833,12 @@ class _LIBCPP_TEMPLATE_VIS function<_Rp(_ArgTypes...)>
835833
__func __f_;
836834

837835
template <class _Fp,
838-
bool = _And< _IsNotSame<__remove_cvref_t<_Fp>, function>, __invokable<_Fp, _ArgTypes...> >::value>
836+
bool = _And<_IsNotSame<__remove_cvref_t<_Fp>, function>, __is_invocable<_Fp, _ArgTypes...> >::value>
839837
struct __callable;
840838
template <class _Fp>
841839
struct __callable<_Fp, true> {
842840
static const bool value =
843-
is_void<_Rp>::value || __is_core_convertible<typename __invoke_of<_Fp, _ArgTypes...>::type, _Rp>::value;
841+
is_void<_Rp>::value || __is_core_convertible<__invoke_result_t<_Fp, _ArgTypes...>, _Rp>::value;
844842
};
845843
template <class _Fp>
846844
struct __callable<_Fp, false> {

libcxx/include/__functional/hash.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -522,7 +522,7 @@ template <class _Key, class _Hash>
522522
using __check_hash_requirements _LIBCPP_NODEBUG =
523523
integral_constant<bool,
524524
is_copy_constructible<_Hash>::value && is_move_constructible<_Hash>::value &&
525-
__invokable_r<size_t, _Hash, _Key const&>::value >;
525+
__is_invocable_r_v<size_t, _Hash, _Key const&> >;
526526

527527
template <class _Key, class _Hash = hash<_Key> >
528528
using __has_enabled_hash _LIBCPP_NODEBUG =

libcxx/include/__functional/mem_fn.h

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -36,14 +36,14 @@ class __mem_fn : public __weak_result_type<_Tp> {
3636

3737
// invoke
3838
template <class... _ArgTypes>
39-
_LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 typename __invoke_of<const _Tp&, _ArgTypes...>::type
40-
operator()(_ArgTypes&&... __args) const _NOEXCEPT_(__nothrow_invokable<const _Tp&, _ArgTypes...>::value) {
39+
_LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 __invoke_result_t<const _Tp&, _ArgTypes...>
40+
operator()(_ArgTypes&&... __args) const _NOEXCEPT_(__is_nothrow_invocable_v<const _Tp&, _ArgTypes...>) {
4141
return std::__invoke(__f_, std::forward<_ArgTypes>(__args)...);
4242
}
4343
};
4444

4545
template <class _Rp, class _Tp>
46-
inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 __mem_fn<_Rp _Tp::*> mem_fn(_Rp _Tp::*__pm) _NOEXCEPT {
46+
inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 __mem_fn<_Rp _Tp::*> mem_fn(_Rp _Tp::* __pm) _NOEXCEPT {
4747
return __mem_fn<_Rp _Tp::*>(__pm);
4848
}
4949

libcxx/include/__functional/reference_wrapper.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -57,7 +57,7 @@ class _LIBCPP_TEMPLATE_VIS reference_wrapper : public __weak_result_type<_Tp> {
5757

5858
// invoke
5959
template <class... _ArgTypes>
60-
_LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 typename __invoke_of<type&, _ArgTypes...>::type
60+
_LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 __invoke_result_t<type&, _ArgTypes...>
6161
operator()(_ArgTypes&&... __args) const
6262
#if _LIBCPP_STD_VER >= 17
6363
// Since is_nothrow_invocable requires C++17 LWG3764 is not backported

libcxx/include/__hash_table

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -652,9 +652,9 @@ struct __enforce_unordered_container_requirements {
652652

653653
template <class _Key, class _Hash, class _Equal>
654654
#ifndef _LIBCPP_CXX03_LANG
655-
_LIBCPP_DIAGNOSE_WARNING(!__invokable<_Equal const&, _Key const&, _Key const&>::value,
655+
_LIBCPP_DIAGNOSE_WARNING(!__is_invocable_v<_Equal const&, _Key const&, _Key const&>,
656656
"the specified comparator type does not provide a viable const call operator")
657-
_LIBCPP_DIAGNOSE_WARNING(!__invokable<_Hash const&, _Key const&>::value,
657+
_LIBCPP_DIAGNOSE_WARNING(!__is_invocable_v<_Hash const&, _Key const&>,
658658
"the specified hash functor does not provide a viable const call operator")
659659
#endif
660660
typename __enforce_unordered_container_requirements<_Key, _Hash, _Equal>::type

libcxx/include/__tree

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -878,7 +878,7 @@ private:
878878

879879
template <class _Tp, class _Compare>
880880
#ifndef _LIBCPP_CXX03_LANG
881-
_LIBCPP_DIAGNOSE_WARNING(!__invokable<_Compare const&, _Tp const&, _Tp const&>::value,
881+
_LIBCPP_DIAGNOSE_WARNING(!__is_invocable_v<_Compare const&, _Tp const&, _Tp const&>,
882882
"the specified comparator type does not provide a viable const call operator")
883883
#endif
884884
int __diagnose_non_const_comparator();

libcxx/include/__type_traits/invoke.h

Lines changed: 62 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,37 @@
2929
# pragma GCC system_header
3030
#endif
3131

32+
// This file defines the following libc++-internal API (back-ported to C++03):
33+
// Any classes may also be aliases to other classes.
34+
//
35+
// template <class... Args>
36+
// decltype(auto) __invoke(Args&&... args) noexcept(noexcept(std::invoke(std::forward<Args>(args...)))) {
37+
// return std::invoke(std::forward<Args>(args)...);
38+
// }
39+
//
40+
// template <class Ret, class... Args>
41+
// Ret __invoke_r(Args&&... args) {
42+
// return std::invoke_r(std::forward<Args>(args)...);
43+
// }
44+
//
45+
// template <class Ret, class Func, class... Args>
46+
// inline const bool __is_invocable_r_v = is_invocable_r_v<Ret, Func, Args...>;
47+
//
48+
// template <class Func, class... Args>
49+
// struct __is_invocable : is_invocable<Func, Args...> {};
50+
//
51+
// template <class Func, class... Args>
52+
// inline const bool __is_invocable_v = is_invocable_v<Func, Args...>;
53+
//
54+
// template <class Func, class... Args>
55+
// inline const bool __is_nothrow_invocable_v = is_nothrow_invocable_v<Func, Args...>;
56+
//
57+
// template <class Func, class... Args>
58+
// struct __invoke_result : invoke_result {};
59+
//
60+
// template <class Func, class... Args>
61+
// using __invoke_result_t = invoke_result_t<Func, Args...>;
62+
3263
_LIBCPP_BEGIN_NAMESPACE_STD
3364

3465
template <class _DecayedFp>
@@ -167,7 +198,7 @@ struct __invokable_r {
167198
static const bool value = type::value;
168199
};
169200
template <class _Fp, class... _Args>
170-
using __invokable = __invokable_r<void, _Fp, _Args...>;
201+
using __is_invocable = __invokable_r<void, _Fp, _Args...>;
171202

172203
template <bool _IsInvokable, bool _IsCVVoid, class _Ret, class _Fp, class... _Args>
173204
struct __nothrow_invokable_r_imp {
@@ -203,11 +234,7 @@ using __nothrow_invokable_r =
203234
__nothrow_invokable_r_imp<__invokable_r<_Ret, _Fp, _Args...>::value, is_void<_Ret>::value, _Ret, _Fp, _Args...>;
204235

205236
template <class _Fp, class... _Args>
206-
using __nothrow_invokable = __nothrow_invokable_r_imp<__invokable<_Fp, _Args...>::value, true, void, _Fp, _Args...>;
207-
208-
template <class _Fp, class... _Args>
209-
struct __invoke_of
210-
: public enable_if<__invokable<_Fp, _Args...>::value, typename __invokable_r<void, _Fp, _Args...>::_Result> {};
237+
using __nothrow_invokable = __nothrow_invokable_r_imp<__is_invocable<_Fp, _Args...>::value, true, void, _Fp, _Args...>;
211238

212239
template <class _Ret, bool = is_void<_Ret>::value>
213240
struct __invoke_void_return_wrapper {
@@ -225,31 +252,51 @@ struct __invoke_void_return_wrapper<_Ret, true> {
225252
}
226253
};
227254

255+
template <class _Func, class... _Args>
256+
inline const bool __is_invocable_v = __is_invocable<_Func, _Args...>::value;
257+
258+
template <class _Ret, class _Func, class... _Args>
259+
inline const bool __is_invocable_r_v = __invokable_r<_Ret, _Func, _Args...>::value;
260+
261+
template <class _Func, class... _Args>
262+
inline const bool __is_nothrow_invocable_v = __nothrow_invokable<_Func, _Args...>::value;
263+
264+
template <class _Func, class... _Args>
265+
struct __invoke_result
266+
: enable_if<__is_invocable_v<_Func, _Args...>, typename __invokable_r<void, _Func, _Args...>::_Result> {};
267+
268+
template <class _Func, class... _Args>
269+
using __invoke_result_t = typename __invoke_result<_Func, _Args...>::type;
270+
271+
template <class _Ret, class... _Args>
272+
_LIBCPP_CONSTEXPR_SINCE_CXX20 _Ret __invoke_r(_Args&&... __args) {
273+
return __invoke_void_return_wrapper<_Ret>::__call(std::forward<_Args>(__args)...);
274+
}
275+
228276
#if _LIBCPP_STD_VER >= 17
229277

230278
// is_invocable
231279

232280
template <class _Fn, class... _Args>
233-
struct _LIBCPP_TEMPLATE_VIS is_invocable : integral_constant<bool, __invokable<_Fn, _Args...>::value> {};
281+
struct _LIBCPP_TEMPLATE_VIS is_invocable : bool_constant<__is_invocable_v<_Fn, _Args...>> {};
234282

235283
template <class _Ret, class _Fn, class... _Args>
236-
struct _LIBCPP_TEMPLATE_VIS is_invocable_r : integral_constant<bool, __invokable_r<_Ret, _Fn, _Args...>::value> {};
284+
struct _LIBCPP_TEMPLATE_VIS is_invocable_r : bool_constant<__is_invocable_r_v<_Ret, _Fn, _Args...>> {};
237285

238286
template <class _Fn, class... _Args>
239-
inline constexpr bool is_invocable_v = is_invocable<_Fn, _Args...>::value;
287+
inline constexpr bool is_invocable_v = __is_invocable_v<_Fn, _Args...>;
240288

241289
template <class _Ret, class _Fn, class... _Args>
242-
inline constexpr bool is_invocable_r_v = is_invocable_r<_Ret, _Fn, _Args...>::value;
290+
inline constexpr bool is_invocable_r_v = __is_invocable_r_v<_Ret, _Fn, _Args...>;
243291

244292
// is_nothrow_invocable
245293

246294
template <class _Fn, class... _Args>
247-
struct _LIBCPP_TEMPLATE_VIS is_nothrow_invocable : integral_constant<bool, __nothrow_invokable<_Fn, _Args...>::value> {
248-
};
295+
struct _LIBCPP_TEMPLATE_VIS is_nothrow_invocable : bool_constant<__nothrow_invokable<_Fn, _Args...>::value> {};
249296

250297
template <class _Ret, class _Fn, class... _Args>
251-
struct _LIBCPP_TEMPLATE_VIS is_nothrow_invocable_r
252-
: integral_constant<bool, __nothrow_invokable_r<_Ret, _Fn, _Args...>::value> {};
298+
struct _LIBCPP_TEMPLATE_VIS is_nothrow_invocable_r : bool_constant<__nothrow_invokable_r<_Ret, _Fn, _Args...>::value> {
299+
};
253300

254301
template <class _Fn, class... _Args>
255302
inline constexpr bool is_nothrow_invocable_v = is_nothrow_invocable<_Fn, _Args...>::value;
@@ -258,7 +305,7 @@ template <class _Ret, class _Fn, class... _Args>
258305
inline constexpr bool is_nothrow_invocable_r_v = is_nothrow_invocable_r<_Ret, _Fn, _Args...>::value;
259306

260307
template <class _Fn, class... _Args>
261-
struct _LIBCPP_TEMPLATE_VIS invoke_result : __invoke_of<_Fn, _Args...> {};
308+
struct _LIBCPP_TEMPLATE_VIS invoke_result : __invoke_result<_Fn, _Args...> {};
262309

263310
template <class _Fn, class... _Args>
264311
using invoke_result_t = typename invoke_result<_Fn, _Args...>::type;

libcxx/include/__type_traits/result_of.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,10 +22,10 @@ _LIBCPP_BEGIN_NAMESPACE_STD
2222

2323
#if _LIBCPP_STD_VER <= 17 || defined(_LIBCPP_ENABLE_CXX20_REMOVED_TYPE_TRAITS)
2424
template <class _Callable>
25-
class _LIBCPP_DEPRECATED_IN_CXX17 result_of;
25+
struct _LIBCPP_DEPRECATED_IN_CXX17 result_of;
2626

2727
template <class _Fp, class... _Args>
28-
class _LIBCPP_TEMPLATE_VIS result_of<_Fp(_Args...)> : public __invoke_of<_Fp, _Args...> {};
28+
struct _LIBCPP_TEMPLATE_VIS result_of<_Fp(_Args...)> : __invoke_result<_Fp, _Args...> {};
2929

3030
# if _LIBCPP_STD_VER >= 14
3131
template <class _Tp>

0 commit comments

Comments
 (0)