std::invoke, std::invoke_r - cppreference.com

From cppreference.com

Defined in header

<functional>

template<classF,class...Args>std::invoke_result_t<F,Args...>invoke(F&&f,Args&&...args)noexcept(/* see below */); (1)(since C++17)
(constexpr since C++20)template<classR,classF,class...Args>constexprRinvoke_r(F&&f,Args&&...args)noexcept(/* see below */); (2)(since C++23)1) Invoke the

Callable

object f with the parameters args as by

INVOKE

(std::forward<F>(f),std::forward<Args>(args)...). This overload participates in overload resolution only if std::is_invocable_v<F,Args...> is true.

2) Invoke the

Callable

object f with the parameters args as by

INVOKE<R>

(std::forward<F>(f),std::forward<Args>(args)...). This overload participates in overload resolution only if std::is_invocable_r_v<R,F,Args...> is true.

Parameters

f -

Callable

object to be invoked args - arguments to pass to fReturn value

1) The value returned by f.

2) The value returned by f, implicitly converted to R, if R is not (possibly

cv-qualified

) void. None otherwise.

Exceptions

1)

noexcept

specification:

noexcept(std::is_nothrow_invocable_v<F,Args...>)2)

noexcept

specification:

noexcept(std::is_nothrow_invocable_r_v<R,F,Args...>)Possible implementation

invoke (1)

namespacedetail{template<class>constexprboolis_reference_wrapper_v=false;template<classU>constexprboolis_reference_wrapper_v<std::reference_wrapper<U>>=true;template<classT>usingremove_cvref_t=std::remove_cv_t<std::remove_reference_t<T>>;template<classC,classPointed,classObject,class...Args>constexprdecltype(auto)invoke_memptr(PointedC::*member,Object&&object,Args&&...args){usingobject_t=remove_cvref_t<Object>;constexprboolis_member_function=std::is_function_v<Pointed>;constexprboolis_wrapped=is_reference_wrapper_v<object_t>;constexprboolis_derived_object=std::is_same_v<C,object_t>||std::is_base_of_v<C,object_t>;ifconstexpr(is_member_function){ifconstexpr(is_derived_object)return(std::forward<Object>(object).*member)(std::forward<Args>(args)...);elseifconstexpr(is_wrapped)return(object.get().*member)(std::forward<Args>(args)...);elsereturn((*std::forward<Object>(object)).*member)(std::forward<Args>(args)...);}else{static_assert(std::is_object_v<Pointed>&&sizeof...(args)==0);ifconstexpr(is_derived_object)returnstd::forward<Object>(object).*member;elseifconstexpr(is_wrapped)returnobject.get().*member;elsereturn(*std::forward<Object>(object)).*member;}}}// namespace detailtemplate<classF,class...Args>constexprstd::invoke_result_t<F,Args...>invoke(F&&f,Args&&...args)noexcept(std::is_nothrow_invocable_v<F,Args...>){ifconstexpr(std::is_member_pointer_v<detail::remove_cvref_t<F>>)returndetail::invoke_memptr(f,std::forward<Args>(args)...);elsereturnstd::forward<F>(f)(std::forward<Args>(args)...);}

invoke_r (2)

template<classR,classF,class...Args>requiresstd::is_invocable_r_v<R,F,Args...>constexprRinvoke_r(F&&f,Args&&...args)noexcept(std::is_nothrow_invocable_r_v<R,F,Args...>){ifconstexpr(std::is_void_v<R>)std::invoke(std::forward<F>(f),std::forward<Args>(args)...);elsereturnstd::invoke(std::forward<F>(f),std::forward<Args>(args)...);}Notes

Feature-test

macro ValueStdFeature

__cpp_lib_invoke

201411L

(C++17)std::invoke, (

1

)

__cpp_lib_invoke_r

202106L

(C++23)std::invoke_r, (

2

)Example

Run this code

#include<functional>#include<iostream>#include<type_traits>structFoo{Foo(intnum):num_(num){}voidprint_add(inti)const{std::cout<<num_+i<<'\n';}intnum_;};voidprint_num(inti){std::cout<<i<<'\n';}structPrintNum{voidoperator()(inti)const{std::cout<<i<<'\n';}};intmain(){std::cout<<"invoke a free function: ";std::invoke(print_num,-9);std::cout<<"invoke a lambda: ";std::invoke([](){print_num(42);});std::cout<<"invoke a member function: ";constFoofoo(314159);std::invoke(&Foo::print_add,foo,1);std::cout<<"invoke (i.e., access) a data member num_: "<<std::invoke(&Foo::num_,foo)<<'\n';std::cout<<"invoke a function object: ";std::invoke(PrintNum(),18);#if defined(__cpp_lib_invoke_r)autoadd=[](intx,inty){returnx+y;};std::cout<<"invoke a lambda converting result to float: ";autoret=std::invoke_r<float>(add,11,22);static_assert(std::is_same<decltype(ret),float>());std::cout<<std::fixed<<ret<<"\ninvoke print_num: ";std::invoke_r<void>(print_num,44);#endif}Possible output:

invoke a free function: -9 invoke a lambda: 42 invoke a member function: 314160 invoke (i.e., access) a data member num_: 314159 invoke a function object: 18 invoke a lambda converting result to float: 33.000000 invoke print_num: 44 See also

mem_fn

(C++11)

creates a function object out of a pointer to a member
(function template)

[edit]

apply

(C++17)

calls a function with a tuple of arguments
(function template)

[edit]

result_ofinvoke_result

(C++11)(removed in C++20)(C++17)

deduces the result type of invoking a callable object with a set of arguments
(class template)

[edit]

is_invocableis_invocable_ris_nothrow_invocableis_nothrow_invocable_r

(C++17)(C++17)(C++17)(C++17)

checks if a type can be invoked (as if by

std::invoke

) with the given argument types
(class template)

[edit]

is_invocable_typeis_invocable_r_typeis_nothrow_invocable_typeis_nothrow_invocable_r_type

(C++26)(C++26)(C++26)(C++26)

checks if the reflected type can be invoked (as if by

std::invoke

) with the given argument types
(function template)

[edit]

is_applicable_typeis_nothrow_applicable_type

(C++26)(C++26)

checks if the callable object can be invoked (as if by

std::invoke

) with a tuple of arguments
(function)

[edit]