Files
cppdraft_translate/cppdraft/func/wrap.md
2025-10-25 03:02:53 +03:00

63 KiB
Raw Blame History

[func.wrap]

22 General utilities library [utilities]

22.10 Function objects [function.objects]

22.10.17 Polymorphic function wrappers [func.wrap]

22.10.17.1 General [func.wrap.general]

1

#

Subclause [func.wrap] describes polymorphic wrapper classes that encapsulate arbitrary callable objects.

2

#

Let t be an object of a type that is a specialization offunction, copyable_function, or move_only_function, such that the target object x of t has a type that is a specialization offunction, copyable_function, or move_only_function.

Each argument of the invocation of x evaluated as part of the invocation of t may alias an argument in the same position in the invocation of t that has the same type, even if the corresponding parameter is not of reference type.

[Example 1: move_only_function<void(T)> f{copyable_function<void(T)>{ {}}}; T t; f(t); // it is unspecified how many copies of T are made — end example]

3

#

Recommended practice: Implementations should avoid double wrapping when constructing polymorphic wrappers from one another.

22.10.17.2 Class bad_function_call [func.wrap.badcall]

1

#

An exception of type bad_function_call is thrown byfunction::operator() ([func.wrap.func.inv]) when the function wrapper object has no target.

namespace std {class bad_function_call : public exception {public:// see [exception] for the specification of the special member functionsconst char* what() const noexcept override; };}

🔗

const char* what() const noexcept override;

2

#

Returns: Animplementation-defined ntbs.

22.10.17.3 Class template function [func.wrap.func]

22.10.17.3.1 General [func.wrap.func.general]

🔗

namespace std {template<class R, class... ArgTypes>class function<R(ArgTypes...)> {public:using result_type = R; // [func.wrap.func.con], construct/copy/destroy function() noexcept; function(nullptr_t) noexcept; function(const function&); function(function&&) noexcept; template function(F&&);

function& operator=(const function&); function& operator=(function&&); function& operator=(nullptr_t) noexcept; template function& operator=(F&&); template function& operator=(reference_wrapper) noexcept; ~function(); // [func.wrap.func.mod], function modifiersvoid swap(function&) noexcept; // [func.wrap.func.cap], function capacityexplicit operator bool() const noexcept; // [func.wrap.func.inv], function invocation R operator()(ArgTypes...) const; // [func.wrap.func.targ], function target accessconst type_info& target_type() const noexcept; template T* target() noexcept; template const T* target() const noexcept; }; template<class R, class... ArgTypes> function(R(*)(ArgTypes...)) -> function<R(ArgTypes...)>; template function(F) -> function<see below>;}

1

#

The function class template provides polymorphic wrappers that generalize the notion of a function pointer.

Wrappers can store, copy, and call arbitrary callable objects ([func.def]), given a call signature ([func.def]).

2

#

The function class template is a call wrapper ([func.def]) whose call signature ([func.def]) is R(ArgTypes...).

3

#

[Note 1:

The types deduced by the deduction guides for function might change in future revisions of C++.

— end note]

22.10.17.3.2 Constructors and destructor [func.wrap.func.con]

🔗

function() noexcept;

1

#

Postconditions: !*this.

🔗

function(nullptr_t) noexcept;

2

#

Postconditions: !*this.

🔗

function(const function& f);

3

#

Postconditions: !*this if !f; otherwise, the target object of *this is a copy of the target object of f.

4

#

Throws: Nothing if f's target is a specialization of reference_wrapper or a function pointer.

Otherwise, may throw bad_alloc or any exception thrown by the copy constructor of the stored callable object.

5

#

Recommended practice: Implementations should avoid the use of dynamically allocated memory for small callable objects, for example, wheref's target is an object holding only a pointer or reference to an object and a member function pointer.

🔗

function(function&& f) noexcept;

6

#

Postconditions: If !f, *this has no target; otherwise, the target of *this is equivalent to the target of f before the construction, andf is in a valid state with an unspecified value.

7

#

Recommended practice: Implementations should avoid the use of dynamically allocated memory for small callable objects, for example, where f's target is an object holding only a pointer or reference to an object and a member function pointer.

🔗

template<class F> function(F&& f);

8

#

Let FD be decay_t.

9

#

Constraints:

is_same_v<remove_cvref_t, function> is false, and

is_invocable_r_v<R, FD&, ArgTypes...> is true.

10

#

Mandates:

is_copy_constructible_v is true, and

is_constructible_v<FD, F> is true.

11

#

Preconditions: FD meets the Cpp17CopyConstructible requirements.

12

#

Postconditions: !*this is true if any of the following hold:

  • (12.1)

    f is a null function pointer value.

  • (12.2)

    f is a null member pointer value.

  • (12.3)

    remove_cvref_t is a specialization of the function class template, and!f is true.

13

#

Otherwise, *this has a target object of type FD direct-non-list-initialized with std::forward(f).

14

#

Throws: Nothing if FD is a specialization of reference_wrapper or a function pointer type.

Otherwise, may throw bad_alloc or any exception thrown by the initialization of the target object.

15

#

Recommended practice: Implementations should avoid the use of dynamically allocated memory for small callable objects, for example, where f refers to an object holding only a pointer or reference to an object and a member function pointer.

🔗

template<class F> function(F) -> function<see below>;

16

#

Constraints: &F::operator() is well-formed when treated as an unevaluated operand and either

F::operator() is a non-static member function anddecltype(&F::operator()) is either of the formR(G::*)(A...) cv &opt noexceptopt or of the formR(*)(G, A...) noexceptopt for a type G, or

F::operator() is a static member function anddecltype(&F::operator()) is of the formR(*)(A...) noexceptopt.

17

#

Remarks: The deduced type is function<R(A...)>.

18

#

[Example 1: void f() {int i{5}; function g = & { return i; }; // deduces function<int(double)>} — end example]

🔗

function& operator=(const function& f);

19

#

Effects: As if by function(f).swap(*this);

20

#

Returns: *this.

🔗

function& operator=(function&& f);

21

#

Effects: Replaces the target of *this with the target of f.

22

#

Returns: *this.

🔗

function& operator=(nullptr_t) noexcept;

23

#

Effects: If *this != nullptr, destroys the target of this.

24

#

Postconditions: !(*this).

25

#

Returns: *this.

🔗

template<class F> function& operator=(F&& f);

26

#

Constraints: is_invocable_r_v<R, decay_t&, ArgTypes...> is true.

27

#

Effects: As if by: function(std::forward(f)).swap(*this);

28

#

Returns: *this.

🔗

template<class F> function& operator=(reference_wrapper<F> f) noexcept;

29

#

Effects: As if by: function(f).swap(*this);

30

#

Returns: *this.

🔗

~function();

31

#

Effects: If *this != nullptr, destroys the target of this.

22.10.17.3.3 Modifiers [func.wrap.func.mod]

🔗

void swap(function& other) noexcept;

1

#

Effects: Interchanges the target objects of *this and other.

22.10.17.3.4 Capacity [func.wrap.func.cap]

🔗

explicit operator bool() const noexcept;

1

#

Returns: true if *this has a target, otherwise false.

22.10.17.3.5 Invocation [func.wrap.func.inv]

🔗

R operator()(ArgTypes... args) const;

1

#

Returns: INVOKE(f, std::forward(args)...) ([func.require]), where f is the target object ([func.def]) of *this.

2

#

Throws: bad_function_call if !*this; otherwise, any exception thrown by the target object.

22.10.17.3.6 Target access [func.wrap.func.targ]

🔗

const type_info& target_type() const noexcept;

1

#

Returns: If *this has a target of type T, typeid(T); otherwise, typeid(void).

🔗

template<class T> T* target() noexcept; template<class T> const T* target() const noexcept;

2

#

Returns: If target_type() == typeid(T) a pointer to the stored function target; otherwise a null pointer.

22.10.17.3.7 Null pointer comparison operator functions [func.wrap.func.nullptr]

🔗

template<class R, class... ArgTypes> bool operator==(const function<R(ArgTypes...)>& f, nullptr_t) noexcept;

1

#

Returns: !f.

22.10.17.3.8 Specialized algorithms [func.wrap.func.alg]

🔗

template<class R, class... ArgTypes> void swap(function<R(ArgTypes...)>& f1, function<R(ArgTypes...)>& f2) noexcept;

1

#

Effects: As if by: f1.swap(f2);

22.10.17.4 Move-only wrapper [func.wrap.move]

22.10.17.4.1 General [func.wrap.move.general]

1

#

The header provides partial specializations of move_only_function for each combination of the possible replacements of the placeholders cv, ref, and noex where

cv is either const or empty,

ref is either &, &&, or empty, and

noex is either true or false.

2

#

For each of the possible combinations of the placeholders mentioned above, there is a placeholder inv-quals defined as follows:

If ref is empty, let inv-quals be cv&,

otherwise, let inv-quals be cv ref.

22.10.17.4.2 Class template move_only_function [func.wrap.move.class]

🔗

namespace std {template<class R, class... ArgTypes>class move_only_function<R(ArgTypes...) cv ref noexcept(noex)> {public:using result_type = R; // [func.wrap.move.ctor], constructors, assignments, and destructor move_only_function() noexcept; move_only_function(nullptr_t) noexcept; move_only_function(move_only_function&&) noexcept; template move_only_function(F&&); template<class T, class... Args>explicit move_only_function(in_place_type_t, Args&&...); template<class T, class U, class... Args>explicit move_only_function(in_place_type_t, initializer_list, Args&&...);

move_only_function& operator=(move_only_function&&); move_only_function& operator=(nullptr_t) noexcept; template move_only_function& operator=(F&&); ~move_only_function(); // [func.wrap.move.inv], invocationexplicit operator bool() const noexcept; R operator()(ArgTypes...) cv ref noexcept(noex); // [func.wrap.move.util], utilityvoid swap(move_only_function&) noexcept; friend void swap(move_only_function&, move_only_function&) noexcept; friend bool operator==(const move_only_function&, nullptr_t) noexcept; private:templatestatic constexpr bool is-callable-from = see below; // exposition only};}

1

#

The move_only_function class template provides polymorphic wrappers that generalize the notion of a callable object ([func.def]).

These wrappers can store, move, and call arbitrary callable objects, given a call signature.

2

#

Recommended practice: Implementations should avoid the use of dynamically allocated memory for a small contained value.

[Note 1:

Such small-object optimization can only be applied to a type T for which is_nothrow_move_constructible_v is true.

— end note]

22.10.17.4.3 Constructors, assignments, and destructor [func.wrap.move.ctor]

🔗

template<class VT> static constexpr bool is-callable-from = see below;

1

#

If noex is true,is-callable-from is equal to:is_nothrow_invocable_r_v<R, VT cv ref, ArgTypes...> && is_nothrow_invocable_r_v<R, VT inv-quals, ArgTypes...>

Otherwise, is-callable-from is equal to:is_invocable_r_v<R, VT cv ref, ArgTypes...> && is_invocable_r_v<R, VT inv-quals, ArgTypes...>

🔗

move_only_function() noexcept; move_only_function(nullptr_t) noexcept;

2

#

Postconditions: *this has no target object.

🔗

move_only_function(move_only_function&& f) noexcept;

3

#

Postconditions: The target object of *this is the target object f had before construction, andf is in a valid state with an unspecified value.

🔗

template<class F> move_only_function(F&& f);

4

#

Let VT be decay_t.

5

#

Constraints:

remove_cvref_t is not the same type as move_only_function, and

remove_cvref_t is not a specialization of in_place_type_t, and

is-callable-from is true.

6

#

Mandates: is_constructible_v<VT, F> is true.

7

#

Preconditions: VT meets the Cpp17Destructible requirements, and if is_move_constructible_v is true,VT meets the Cpp17MoveConstructible requirements.

8

#

Postconditions: *this has no target object if any of the following hold:

f is a null function pointer value, or

f is a null member pointer value, or

remove_cvref_t is a specialization of the move_only_function class template, and f has no target object.

Otherwise, *this has a target object of type VT direct-non-list-initialized with std::forward(f).

9

#

Throws: Any exception thrown by the initialization of the target object.

May throw bad_alloc unless VT is a function pointer or a specialization of reference_wrapper.

🔗

template<class T, class... Args> explicit move_only_function(in_place_type_t<T>, Args&&... args);

10

#

Let VT be decay_t.

11

#

Constraints:

is_constructible_v<VT, Args...> is true, and

is-callable-from is true.

12

#

Mandates: VT is the same type as T.

13

#

Preconditions: VT meets the Cpp17Destructible requirements, and if is_move_constructible_v is true,VT meets the Cpp17MoveConstructible requirements.

14

#

Postconditions: *this has a target object of type VT direct-non-list-initialized with std::forward(args)....

15

#

Throws: Any exception thrown by the initialization of the target object.

May throw bad_alloc unless VT is a function pointer or a specialization of reference_wrapper.

🔗

template<class T, class U, class... Args> explicit move_only_function(in_place_type_t<T>, initializer_list<U> ilist, Args&&... args);

16

#

Let VT be decay_t.

17

#

Constraints:

is_constructible_v<VT, initializer_list&, Args...> istrue, and

is-callable-from is true.

18

#

Mandates: VT is the same type as T.

19

#

Preconditions: VT meets the Cpp17Destructible requirements, and if is_move_constructible_v is true,VT meets the Cpp17MoveConstructible requirements.

20

#

Postconditions: *this has a target object of type VT direct-non-list-initialized withilist, std::forward(args)....

21

#

Throws: Any exception thrown by the initialization of the target object.

May throw bad_alloc unless VT is a function pointer or a specialization of reference_wrapper.

🔗

move_only_function& operator=(move_only_function&& f);

22

#

Effects: Equivalent to: move_only_function(std::move(f)).swap(*this);

23

#

Returns: *this.

🔗

move_only_function& operator=(nullptr_t) noexcept;

24

#

Effects: Destroys the target object of *this, if any.

25

#

Returns: *this.

🔗

template<class F> move_only_function& operator=(F&& f);

26

#

Effects: Equivalent to: move_only_function(std::forward(f)).swap(*this);

27

#

Returns: *this.

🔗

~move_only_function();

28

#

Effects: Destroys the target object of *this, if any.

22.10.17.4.4 Invocation [func.wrap.move.inv]

🔗

explicit operator bool() const noexcept;

1

#

Returns: true if *this has a target object, otherwise false.

🔗

R operator()(ArgTypes... args) cv ref noexcept(noex);

2

#

Preconditions: *this has a target object.

3

#

Effects: Equivalent to:return INVOKE(static_cast<F inv-quals>(f), std::forward(args)...); where f is an lvalue designating the target object of *this andF is the type of f.

22.10.17.4.5 Utility [func.wrap.move.util]

🔗

void swap(move_only_function& other) noexcept;

1

#

Effects: Exchanges the target objects of *this and other.

🔗

friend void swap(move_only_function& f1, move_only_function& f2) noexcept;

2

#

Effects: Equivalent to f1.swap(f2).

🔗

friend bool operator==(const move_only_function& f, nullptr_t) noexcept;

3

#

Returns: true if f has no target object, otherwise false.

22.10.17.5 Copyable wrapper [func.wrap.copy]

22.10.17.5.1 General [func.wrap.copy.general]

1

#

The header provides partial specializations of copyable_function for each combination of the possible replacements of the placeholders cv, ref, and noex where

cv is either const or empty,

ref is either &, &&, or empty, and

noex is either true or false.

2

#

For each of the possible combinations of the placeholders mentioned above, there is a placeholder inv-quals defined as follows:

If ref is empty, let inv-quals be cv&,

otherwise, let inv-quals be cv ref.

22.10.17.5.2 Class template copyable_function [func.wrap.copy.class]

🔗

namespace std {template<class R, class... ArgTypes>class copyable_function<R(ArgTypes...) cv ref noexcept(noex)> {public:using result_type = R; // [func.wrap.copy.ctor], constructors, assignments, and destructor copyable_function() noexcept; copyable_function(nullptr_t) noexcept; copyable_function(const copyable_function&); copyable_function(copyable_function&&) noexcept; template copyable_function(F&&); template<class T, class... Args>explicit copyable_function(in_place_type_t, Args&&...); template<class T, class U, class... Args>explicit copyable_function(in_place_type_t, initializer_list, Args&&...);

copyable_function& operator=(const copyable_function&); copyable_function& operator=(copyable_function&&); copyable_function& operator=(nullptr_t) noexcept; template copyable_function& operator=(F&&); ~copyable_function(); // [func.wrap.copy.inv], invocationexplicit operator bool() const noexcept; R operator()(ArgTypes...) cv ref noexcept(noex); // [func.wrap.copy.util], utilityvoid swap(copyable_function&) noexcept; friend void swap(copyable_function&, copyable_function&) noexcept; friend bool operator==(const copyable_function&, nullptr_t) noexcept; private:templatestatic constexpr bool is-callable-from = see below; // exposition only};}

1

#

The copyable_function class template provides polymorphic wrappers that generalize the notion of a callable object ([func.def]).

These wrappers can store, copy, move, and call arbitrary callable objects, given a call signature.

2

#

Recommended practice: Implementations should avoid the use of dynamically allocated memory for a small contained value.

[Note 1:

Such small-object optimization can only be applied to a type T for which is_nothrow_move_constructible_v is true.

— end note]

22.10.17.5.3 Constructors, assignments, and destructor [func.wrap.copy.ctor]

🔗

template<class VT> static constexpr bool is-callable-from = see below;

1

#

If noex is true,is-callable-from is equal to:is_nothrow_invocable_r_v<R, VT cv ref, ArgTypes...> && is_nothrow_invocable_r_v<R, VT inv-quals, ArgTypes...>

Otherwise, is-callable-from is equal to:is_invocable_r_v<R, VT cv ref, ArgTypes...> && is_invocable_r_v<R, VT inv-quals, ArgTypes...>

🔗

copyable_function() noexcept; copyable_function(nullptr_t) noexcept;

2

#

Postconditions: *this has no target object.

🔗

copyable_function(const copyable_function& f);

3

#

Postconditions: *this has no target object if f had no target object.

Otherwise, the target object of *this is a copy of the target object of f.

4

#

Throws: Any exception thrown by the initialization of the target object.

May throw bad_alloc.

🔗

copyable_function(copyable_function&& f) noexcept;

5

#

Postconditions: The target object of *this is the target object f had before construction, andf is in a valid state with an unspecified value.

🔗

template<class F> copyable_function(F&& f);

6

#

Let VT be decay_t.

7

#

Constraints:

remove_cvref_t is not the same type as copyable_function, and

remove_cvref_t is not a specialization of in_place_type_t, and

is-callable-from is true.

8

#

Mandates:

is_constructible_v<VT, F> is true, and

is_copy_constructible_v is true.

9

#

Preconditions: VT meets the Cpp17Destructible andCpp17CopyConstructible requirements.

10

#

Postconditions: *this has no target object if any of the following hold:

f is a null function pointer value, or

f is a null member pointer value, or

remove_cvref_t is a specialization of the copyable_function class template, and f has no target object.

Otherwise, *this has a target object of type VT direct-non-list-initialized with std::forward(f).

11

#

Throws: Any exception thrown by the initialization of the target object.

May throw bad_alloc unless VT is a function pointer or a specialization of reference_wrapper.

🔗

template<class T, class... Args> explicit copyable_function(in_place_type_t<T>, Args&&... args);

12

#

Let VT be decay_t.

13

#

Constraints:

is_constructible_v<VT, Args...> is true, and

is-callable-from is true.

14

#

Mandates:

VT is the same type as T, and

is_copy_constructible_v is true.

15

#

Preconditions: VT meets the Cpp17Destructible andCpp17CopyConstructible requirements.

16

#

Postconditions: *this has a target object of type VT direct-non-list-initialized with std::forward(args)....

17

#

Throws: Any exception thrown by the initialization of the target object.

May throw bad_alloc unless VT is a pointer or a specialization of reference_wrapper.

🔗

template<class T, class U, class... Args> explicit copyable_function(in_place_type_t<T>, initializer_list<U> ilist, Args&&... args);

18

#

Let VT be decay_t.

19

#

Constraints:

is_constructible_v<VT, initializer_list&, Args...> istrue, and

is-callable-from is true.

20

#

Mandates:

VT is the same type as T, and

is_copy_constructible_v is true.

21

#

Preconditions: VT meets the Cpp17Destructible andCpp17CopyConstructible requirements.

22

#

Postconditions: *this has a target object of type VT direct-non-list-initialized withilist, std::forward(args)....

23

#

Throws: Any exception thrown by the initialization of the target object.

May throw bad_alloc unless VT is a pointer or a specialization of reference_wrapper.

🔗

copyable_function& operator=(const copyable_function& f);

24

#

Effects: Equivalent to: copyable_function(f).swap(*this);

25

#

Returns: *this.

🔗

copyable_function& operator=(copyable_function&& f);

26

#

Effects: Equivalent to: copyable_function(std::move(f)).swap(*this);

27

#

Returns: *this.

🔗

copyable_function& operator=(nullptr_t) noexcept;

28

#

Effects: Destroys the target object of *this, if any.

29

#

Returns: *this.

🔗

template<class F> copyable_function& operator=(F&& f);

30

#

Effects: Equivalent to: copyable_function(std::forward(f)).swap(*this);

31

#

Returns: *this.

🔗

~copyable_function();

32

#

Effects: Destroys the target object of *this, if any.

22.10.17.5.4 Invocation [func.wrap.copy.inv]

🔗

explicit operator bool() const noexcept;

1

#

Returns: true if *this has a target object, otherwise false.

🔗

R operator()(ArgTypes... args) cv ref noexcept(noex);

2

#

Preconditions: *this has a target object.

3

#

Effects: Equivalent to:return INVOKE(static_cast<F inv-quals>(f), std::forward(args)...); where f is an lvalue designating the target object of *this andF is the type of f.

22.10.17.5.5 Utility [func.wrap.copy.util]

🔗

void swap(copyable_function& other) noexcept;

1

#

Effects: Exchanges the target objects of *this and other.

🔗

friend void swap(copyable_function& f1, copyable_function& f2) noexcept;

2

#

Effects: Equivalent to f1.swap(f2).

🔗

friend bool operator==(const copyable_function& f, nullptr_t) noexcept;

3

#

Returns: true if f has no target object, otherwise false.

22.10.17.6 Non-owning wrapper [func.wrap.ref]

22.10.17.6.1 General [func.wrap.ref.general]

1

#

The header provides partial specializations of function_ref for each combination of the possible replacements of the placeholders cv and noex where:

cv is either const or empty, and

noex is either true or false.

22.10.17.6.2 Class template function_ref [func.wrap.ref.class]

🔗

namespace std {template<class R, class... ArgTypes>class function_ref<R(ArgTypes...) cv noexcept(noex)> {public:// [func.wrap.ref.ctor], constructors and assignment operatorstemplate function_ref(F*) noexcept; template constexpr function_ref(F&&) noexcept; template constexpr function_ref(nontype_t) noexcept; template<auto f, class U> constexpr function_ref(nontype_t, U&&) noexcept; template<auto f, class T> constexpr function_ref(nontype_t, cv T*) noexcept; constexpr function_ref(const function_ref&) noexcept = default; constexpr function_ref& operator=(const function_ref&) noexcept = default; template function_ref& operator=(T) = delete; // [func.wrap.ref.inv], invocation R operator()(ArgTypes...) const noexcept(noex); private:template<class... T>static constexpr bool is-invocable-using = see below; // exposition only R (thunk-ptr)(BoundEntityType, Args&&...) noexcept(noex); // *exposition only*BoundEntityType* bound-entity; // exposition only}; // [func.wrap.ref.deduct], deduction guidestemplate function_ref(F*) -> function_ref; template function_ref(nontype_t) -> function_ref<see below>; template<auto f, class T> function_ref(nontype_t, T&&) -> function_ref<see below>;}

1

#

An object of classfunction_ref<R(Args...) cv noexcept(noex)> stores a pointer to function thunk-ptr and an object bound-entity.

bound-entity has an unspecified trivially copyable type BoundEntityType, that models copyable and is capable of storing a pointer to object value or a pointer to function value.

The type of thunk-ptr isR(*)(BoundEntityType, Args&&...) noexcept(noex).

2

#

Each specialization of function_ref is a trivially copyable type ([basic.types.general]) that models copyable.

3

#

Within [func.wrap.ref],call-args is an argument pack with elements such thatdecltype((call-args))... denoteArgs&&... respectively.

22.10.17.6.3 Constructors and assignment operators [func.wrap.ref.ctor]

🔗

template<class... T> static constexpr bool is-invocable-using = see below;

1

#

If noex is true,is-invocable-using<T...> is equal to:is_nothrow_invocable_r_v<R, T..., ArgTypes...>

Otherwise, is-invocable-using<T...> is equal to:is_invocable_r_v<R, T..., ArgTypes...>

🔗

template<class F> function_ref(F* f) noexcept;

2

#

Constraints:

is_function_v is true, and

is-invocable-using is true.

3

#

Preconditions: f is not a null pointer.

4

#

Effects: Initializesbound-entity with f, andthunk-ptr with the address of a function thunk such thatthunk(bound-entity, call-args...) is expression-equivalent ([defns.expression.equivalent]) toinvoke_r(f, call-args...).

🔗

template<class F> constexpr function_ref(F&& f) noexcept;

5

#

Let T be remove_reference_t.

6

#

Constraints:

remove_cvref_t is not the same type as function_ref,

is_member_pointer_v is false, and

is-invocable-using<cv T&> is true.

7

#

Effects: Initializesbound-entity with addressof(f), andthunk-ptr with the address of a function thunk such thatthunk(bound-entity, call-args...) is expression-equivalent ([defns.expression.equivalent]) toinvoke_r(static_cast<cv T&>(f), call-args...).

🔗

template<auto f> constexpr function_ref(nontype_t<f>) noexcept;

8

#

Let F be decltype(f).

9

#

Constraints: is-invocable-using is true.

10

#

Mandates: If is_pointer_v || is_member_pointer_v is true, then f != nullptr is true.

11

#

Effects: Initializesbound-entity with a pointer to an unspecified object or null pointer value, andthunk-ptr with the address of a function thunk such thatthunk(bound-entity, call-args...) is expression-equivalent ([defns.expression.equivalent]) toinvoke_r(f, call-args...).

🔗

template<auto f, class U> constexpr function_ref(nontype_t<f>, U&& obj) noexcept;

12

#

Let T be remove_reference_t andF be decltype(f).

13

#

Constraints:

is_rvalue_reference_v<U&&> is false, and

is-invocable-using<F, cv T&> is true.

14

#

Mandates: If is_pointer_v || is_member_pointer_v is true, then f != nullptr is true.

15

#

Effects: Initializesbound-entity with addressof(obj), andthunk-ptr with the address of a function thunk such thatthunk(bound-entity, call-args...) is expression-equivalent ([defns.expression.equivalent]) toinvoke_r(f, static_cast<cv T&>(obj), call-args...).

🔗

template<auto f, class T> constexpr function_ref(nontype_t<f>, cv T* obj) noexcept;

16

#

Let F be decltype(f).

17

#

Constraints: is-invocable-using<F, cv T*> is true.

18

#

Mandates: If is_pointer_v || is_member_pointer_v is true, then f != nullptr is true.

19

#

Preconditions: If is_member_pointer_v is true,obj is not a null pointer.

20

#

Effects: Initializesbound-entity with obj, andthunk-ptr with the address of a function thunk such thatthunk(bound-entity, call-args...) is expression-equivalent ([defns.expression.equivalent]) toinvoke_r(f, obj, call-args...).

🔗

template<class T> function_ref& operator=(T) = delete;

21

#

Constraints:

T is not the same type as function_ref,

is_pointer_v is false, and

T is not a specialization of nontype_t.

22.10.17.6.4 Invocation [func.wrap.ref.inv]

🔗

R operator()(ArgTypes... args) const noexcept(noex);

1

#

Effects: Equivalent to:return thunk-ptr(bound-entity, std::forward(args)...);

22.10.17.6.5 Deduction guides [func.wrap.ref.deduct]

🔗

template<class F> function_ref(F*) -> function_ref<F>;

1

#

Constraints: is_function_v is true.

🔗

template<auto f> function_ref(nontype_t<f>) -> function_ref<see below>;

2

#

Let F be remove_pointer_t<decltype(f)>.

3

#

Constraints: is_function_v is true.

4

#

Remarks: The deduced type is function_ref.

🔗

template<auto f, class T> function_ref(nontype_t<f>, T&&) -> function_ref<see below>;

5

#

Let F be decltype(f).

6

#

Constraints:

F is of the formR(G::*)(A...) cv &opt noexcept(E) for a type G, or

F is of the formM G::* for a type G and an object type M, in which case let R be invoke_result_t<F, T&>,A... be an empty pack, andE be false, or

F is of the formR(*)(G, A...) noexcept(E) for a type G.

7

#

Remarks: The deduced type is function_ref<R(A...) noexcept(E)>.