A function object type - это object type тип, который может быть типом postfix-expressionв вызове функции ([expr.call], [over.match.call]).222 A function object - объект типа функционального объекта. В тех местах, где можно было бы ожидать передачи указателя на функцию в алгоритмический шаблон (пункт [algorithms]), указывается интерфейс для приема объекта функции. Это не только заставляет алгоритмические шаблоны работать с указателями на функции, но также позволяет им работать с произвольными объектами функций.
Такой тип является указателем на функцию или типом класса, который имеет член operator() или тип класса, который имеет преобразование в указатель на функцию.
namespace std { // [func.invoke], invoke template <class F, class... Args> invoke_result_t<F, Args...> invoke(F&& f, Args&&... args) noexcept(is_nothrow_invocable_v<F, Args...>); // [refwrap], reference_wrapper template <class T> class reference_wrapper; template <class T> reference_wrapper<T> ref(T&) noexcept; template <class T> reference_wrapper<const T> cref(const T&) noexcept; template <class T> void ref(const T&&) = delete; template <class T> void cref(const T&&) = delete; template <class T> reference_wrapper<T> ref(reference_wrapper<T>) noexcept; template <class T> reference_wrapper<const T> cref(reference_wrapper<T>) noexcept; // [arithmetic.operations], arithmetic operations template <class T = void> struct plus; template <class T = void> struct minus; template <class T = void> struct multiplies; template <class T = void> struct divides; template <class T = void> struct modulus; template <class T = void> struct negate; template <> struct plus<void>; template <> struct minus<void>; template <> struct multiplies<void>; template <> struct divides<void>; template <> struct modulus<void>; template <> struct negate<void>; // [comparisons], comparisons template <class T = void> struct equal_to; template <class T = void> struct not_equal_to; template <class T = void> struct greater; template <class T = void> struct less; template <class T = void> struct greater_equal; template <class T = void> struct less_equal; template <> struct equal_to<void>; template <> struct not_equal_to<void>; template <> struct greater<void>; template <> struct less<void>; template <> struct greater_equal<void>; template <> struct less_equal<void>; // [logical.operations], logical operations template <class T = void> struct logical_and; template <class T = void> struct logical_or; template <class T = void> struct logical_not; template <> struct logical_and<void>; template <> struct logical_or<void>; template <> struct logical_not<void>; // [bitwise.operations], bitwise operations template <class T = void> struct bit_and; template <class T = void> struct bit_or; template <class T = void> struct bit_xor; template <class T = void> struct bit_not; template <> struct bit_and<void>; template <> struct bit_or<void>; template <> struct bit_xor<void>; template <> struct bit_not<void>; // [func.not_fn], function template not_fn template <class F> unspecified not_fn(F&& f); // [func.bind], bind template<class T> struct is_bind_expression; template<class T> struct is_placeholder; template<class F, class... BoundArgs> unspecified bind(F&&, BoundArgs&&...); template<class R, class F, class... BoundArgs> unspecified bind(F&&, BoundArgs&&...); namespace placeholders { // M is the implementation-defined number of placeholders see below _1; see below _2; . . . see below _M; } // [func.memfn], member function adaptors template<class R, class T> unspecified mem_fn(R T::*) noexcept; // [func.wrap], polymorphic function wrappers class bad_function_call; template<class> class function; // not defined template<class R, class... ArgTypes> class function<R(ArgTypes...)>; template<class R, class... ArgTypes> void swap(function<R(ArgTypes...)>&, function<R(ArgTypes...)>&) noexcept; template<class R, class... ArgTypes> bool operator==(const function<R(ArgTypes...)>&, nullptr_t) noexcept; template<class R, class... ArgTypes> bool operator==(nullptr_t, const function<R(ArgTypes...)>&) noexcept; template<class R, class... ArgTypes> bool operator!=(const function<R(ArgTypes...)>&, nullptr_t) noexcept; template<class R, class... ArgTypes> bool operator!=(nullptr_t, const function<R(ArgTypes...)>&) noexcept; // [func.search], searchers template<class ForwardIterator, class BinaryPredicate = equal_to<>> class default_searcher; template<class RandomAccessIterator, class Hash = hash<typename iterator_traits<RandomAccessIterator>::value_type>, class BinaryPredicate = equal_to<>> class boyer_moore_searcher; template<class RandomAccessIterator, class Hash = hash<typename iterator_traits<RandomAccessIterator>::value_type>, class BinaryPredicate = equal_to<>> class boyer_moore_horspool_searcher; // [unord.hash], hash function primary template template <class T> struct hash; // [func.bind], function object binders template <class T> inline constexpr bool is_bind_expression_v = is_bind_expression<T>::value; template <class T> inline constexpr int is_placeholder_v = is_placeholder<T>::value; }
[ Example: Если C ++ программа хочет иметь поэлементное сложение двух векторов a и b содержащее double и поместить результат в aэто можно сделать:
transform(a.begin(), a.end(), b.begin(), a.begin(), plus<double>());
— end example ]
A call signature - это имя возвращаемого типа, за которым следует список в скобках, разделенных запятыми, из нуля или более типов аргументов.
A call wrapper type - это тип, который содержит вызываемый объект и поддерживает операцию вызова, которая перенаправляет на этот объект.
Определите INVOKE(f, t1, t2, ..., tN) следующее:
(t1.*f)(t2, ..., tN) when f - указатель на функцию-член класса T и is_base_of_v<T, decay_t<decltype(t1)>> is true;
(t1.get().*f)(t2, ..., tN) when f - указатель на функцию-член класса T и decay_t<decltype(t1)> является специализацией reference_wrapper;
((*t1).*f)(t2, ..., tN) when f является указателем на функцию-член класса T и t1 не удовлетворяет двум предыдущим элементам;
t1.*f когда N == 1 и f является указателем на член данных класса T и is_base_of_v<T, decay_t<decltype(t1)>> является true;
t1.get().*f когда N == 1 и f является указателем на член данных класса T и decay_t<decltype(t1)> является специализацией reference_wrapper;
(*t1).*f когда N == 1 и f является указателем на член данных класса T и t1 не удовлетворяет двум предыдущим элементам;
f(t1, t2, ..., tN) во всех остальных случаях.
Определите INVOKE<R>(f, t1, t2, ..., tN) как static_cast<void>(INVOKE(f, t1, t2, ..., tN)) если бы R есть cv void, иначе INVOKE(f, t1, t2, ..., tN) неявно преобразовать в R.
Каждый call wrapper должен быть MoveConstructible. A forwarding call wrapper - это оболочка вызова, которая может быть вызвана с произвольным списком аргументов и доставляет аргументы обернутому вызываемому объекту в виде ссылок. Этот шаг пересылки должен гарантировать, что аргументы rvalue доставляются как ссылки rvalue, а аргументы lvalue доставляются как ссылки lvalue. A simple call wrapper - это оболочка переадресации вызовов, которая есть CopyConstructible и, CopyAssignable чей конструктор копирования, конструктор перемещения и оператор присваивания не генерируют исключения. [ Note: В типичной реализации оболочки переадресации вызовов имеют перегруженный оператор вызова функции вида
template<class... UnBoundArgs>
R operator()(UnBoundArgs&&... unbound_args) cv-qual;
— end note ]
template <class F, class... Args>
invoke_result_t<F, Args...> invoke(F&& f, Args&&... args)
noexcept(is_nothrow_invocable_v<F, Args...>);
Returns: INVOKE(std::forward<F>(f), std::forward<Args>(args)...) ([func.require]).
namespace std { template <class T> class reference_wrapper { public : // types using type = T; // construct/copy/destroy reference_wrapper(T&) noexcept; reference_wrapper(T&&) = delete; // do not bind to temporary objects reference_wrapper(const reference_wrapper& x) noexcept; // assignment reference_wrapper& operator=(const reference_wrapper& x) noexcept; // access operator T& () const noexcept; T& get() const noexcept; // invocation template <class... ArgTypes> invoke_result_t<T&, ArgTypes...> operator() (ArgTypes&&...) const; }; template<class T> reference_wrapper(reference_wrapper<T>) -> reference_wrapper<T>; }
reference_wrapper<T> - это CopyConstructible и CopyAssignable оболочка вокруг ссылки на объект или функцию типа T.
reference_wrapper(T& t) noexcept;
reference_wrapper(const reference_wrapper& x) noexcept;
reference_wrapper& operator=(const reference_wrapper& x) noexcept;
operator T& () const noexcept;
T& get() const noexcept;
template <class... ArgTypes>
invoke_result_t<T&, ArgTypes...>
operator()(ArgTypes&&... args) const;
Returns: INVOKE(get(), std::forward<ArgTypes>(args)...). ([func.require])
template <class T> reference_wrapper<T> ref(T& t) noexcept;
template <class T> reference_wrapper<T> ref(reference_wrapper<T> t) noexcept;
template <class T> reference_wrapper<const T> cref(const T& t) noexcept;
template <class T> reference_wrapper<const T> cref(reference_wrapper<T> t) noexcept;
Библиотека предоставляет базовые классы функциональных объектов для всех арифметических операторов языка ([expr.mul], [expr.add]).
template <class T = void> struct plus {
constexpr T operator()(const T& x, const T& y) const;
};
constexpr T operator()(const T& x, const T& y) const;
template <> struct plus<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) + std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) + std::forward<U>(u));
template <class T = void> struct minus {
constexpr T operator()(const T& x, const T& y) const;
};
constexpr T operator()(const T& x, const T& y) const;
template <> struct minus<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) - std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) - std::forward<U>(u));
template <class T = void> struct multiplies {
constexpr T operator()(const T& x, const T& y) const;
};
constexpr T operator()(const T& x, const T& y) const;
template <> struct multiplies<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) * std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) * std::forward<U>(u));
template <class T = void> struct divides {
constexpr T operator()(const T& x, const T& y) const;
};
constexpr T operator()(const T& x, const T& y) const;
template <> struct divides<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) / std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) / std::forward<U>(u));
template <class T = void> struct modulus {
constexpr T operator()(const T& x, const T& y) const;
};
constexpr T operator()(const T& x, const T& y) const;
template <> struct modulus<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) % std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) % std::forward<U>(u));
template <class T = void> struct negate {
constexpr T operator()(const T& x) const;
};
constexpr T operator()(const T& x) const;
template <> struct negate<void> {
template <class T> constexpr auto operator()(T&& t) const
-> decltype(-std::forward<T>(t));
using is_transparent = unspecified;
};
template <class T> constexpr auto operator()(T&& t) const
-> decltype(-std::forward<T>(t));
Библиотека предоставляет базовые классы объектов функций для всех операторов сравнения на языке ([expr.rel], [expr.eq]).
Для шаблонов less, greater, less_equalи greater_equal, специализации для любого типа указателя дают строгий общий порядок , который соответствует числу тех специальностей , а также в соответствии с частичным порядком наложенного с помощью встроенного в операторах <, >, <=, >=. [ Note: Когда a < b хорошо определены для указателей a и b типа P, это означает (a < b) == less<P>(a, b), (a > b) == greater<P>(a, b)и так далее. ] Для шаблонных специализаций , , и , если оператор вызова вызывает встроенный оператор сравнения указателей, оператор вызова дает строгий общий порядок , который соответствует числу тех специализаций и также соответствует частичному порядка , навязанному тем встроенному операторы. — end note less<void> greater<void>less_equal<void> greater_equal<void>
template <class T = void> struct equal_to {
constexpr bool operator()(const T& x, const T& y) const;
};
constexpr bool operator()(const T& x, const T& y) const;
template <> struct equal_to<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) == std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) == std::forward<U>(u));
template <class T = void> struct not_equal_to {
constexpr bool operator()(const T& x, const T& y) const;
};
constexpr bool operator()(const T& x, const T& y) const;
template <> struct not_equal_to<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) != std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) != std::forward<U>(u));
template <class T = void> struct greater {
constexpr bool operator()(const T& x, const T& y) const;
};
constexpr bool operator()(const T& x, const T& y) const;
template <> struct greater<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) > std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) > std::forward<U>(u));
template <class T = void> struct less {
constexpr bool operator()(const T& x, const T& y) const;
};
constexpr bool operator()(const T& x, const T& y) const;
template <> struct less<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) < std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) < std::forward<U>(u));
template <class T = void> struct greater_equal {
constexpr bool operator()(const T& x, const T& y) const;
};
constexpr bool operator()(const T& x, const T& y) const;
template <> struct greater_equal<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) >= std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) >= std::forward<U>(u));
template <class T = void> struct less_equal {
constexpr bool operator()(const T& x, const T& y) const;
};
constexpr bool operator()(const T& x, const T& y) const;
template <> struct less_equal<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) <= std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) <= std::forward<U>(u));
Библиотека содержит основные классы объектов функции для всех логических операторов в языке ([expr.log.and], [expr.log.or], [expr.unary.op]).
template <class T = void> struct logical_and {
constexpr bool operator()(const T& x, const T& y) const;
};
constexpr bool operator()(const T& x, const T& y) const;
template <> struct logical_and<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) && std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) && std::forward<U>(u));
template <class T = void> struct logical_or {
constexpr bool operator()(const T& x, const T& y) const;
};
constexpr bool operator()(const T& x, const T& y) const;
template <> struct logical_or<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) || std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) || std::forward<U>(u));
template <class T = void> struct logical_not {
constexpr bool operator()(const T& x) const;
};
constexpr bool operator()(const T& x) const;
template <> struct logical_not<void> {
template <class T> constexpr auto operator()(T&& t) const
-> decltype(!std::forward<T>(t));
using is_transparent = unspecified;
};
template <class T> constexpr auto operator()(T&& t) const
-> decltype(!std::forward<T>(t));
Библиотека содержит основные классы объектов функции для всех операторов поразрядных на языке ([expr.bit.and], [expr.or], [expr.xor], [expr.unary.op]).
template <class T = void> struct bit_and {
constexpr T operator()(const T& x, const T& y) const;
};
constexpr T operator()(const T& x, const T& y) const;
template <> struct bit_and<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) & std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) & std::forward<U>(u));
template <class T = void> struct bit_or {
constexpr T operator()(const T& x, const T& y) const;
};
constexpr T operator()(const T& x, const T& y) const;
template <> struct bit_or<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) | std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) | std::forward<U>(u));
template <class T = void> struct bit_xor {
constexpr T operator()(const T& x, const T& y) const;
};
constexpr T operator()(const T& x, const T& y) const;
template <> struct bit_xor<void> {
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) ^ std::forward<U>(u));
using is_transparent = unspecified;
};
template <class T, class U> constexpr auto operator()(T&& t, U&& u) const
-> decltype(std::forward<T>(t) ^ std::forward<U>(u));
template <class T = void> struct bit_not {
constexpr T operator()(const T& x) const;
};
constexpr T operator()(const T& x) const;
template <> struct bit_not<void> {
template <class T> constexpr auto operator()(T&& t) const
-> decltype(~std::forward<T>(t));
using is_transparent = unspecified;
};
template <class T> constexpr auto operator()(T&&) const
-> decltype(~std::forward<T>(t));
template <class F> unspecified not_fn(F&& f);
Effects: Эквивалентен return call_wrapper(std::forward<F>(f)); where call_wrapper класс только для показа, определенный следующим образом:
class call_wrapper { using FD = decay_t<F>; FD fd; explicit call_wrapper(F&& f); public: call_wrapper(call_wrapper&&) = default; call_wrapper(const call_wrapper&) = default; template<class... Args> auto operator()(Args&&...) & -> decltype(!declval<invoke_result_t<FD&, Args...>>()); template<class... Args> auto operator()(Args&&...) const& -> decltype(!declval<invoke_result_t<const FD&, Args...>>()); template<class... Args> auto operator()(Args&&...) && -> decltype(!declval<invoke_result_t<FD, Args...>>()); template<class... Args> auto operator()(Args&&...) const&& -> decltype(!declval<invoke_result_t<const FD, Args...>>()); };
explicit call_wrapper(F&& f);
Requires: FD должны удовлетворять требованиям MoveConstructible. is_constructible_v<FD, F> будет true. fd должен быть callable object.
template<class... Args>
auto operator()(Args&&... args) &
-> decltype(!declval<invoke_result_t<FD&, Args...>>());
template<class... Args>
auto operator()(Args&&... args) const&
-> decltype(!declval<invoke_result_t<const FD&, Args...>>());
template<class... Args>
auto operator()(Args&&... args) &&
-> decltype(!declval<invoke_result_t<FD, Args...>>());
template<class... Args>
auto operator()(Args&&... args) const&&
-> decltype(!declval<invoke_result_t<const FD, Args...>>());
Effects: Эквивалентен:
return !INVOKE(std::move(fd), std::forward<Args>(args)...); // see [func.require]
namespace std {
template<class T> struct is_bind_expression; // see below
}
Шаблон класса is_bind_expression можно использовать для обнаружения функциональных объектов, сгенерированных bind. Шаблон функции bind используется is_bind_expression для обнаружения подвыражений.
Экземпляры is_bind_expression шаблона должны соответствовать UnaryTypeTrait требованиям. Реализация должна предоставлять определение, которое имеет базовую характеристику true_type if T является типом, возвращаемым из bind, в противном случае он должен иметь базовую характеристику false_type. Программа может специализировать этот шаблон для определяемого пользователем типа, T чтобы он имел базовую характеристику, true_type указывающую, что T следует рассматривать как подвыражение в bind вызове.
namespace std {
template<class T> struct is_placeholder; // see below
}
Шаблон класса is_placeholder может быть использован для обнаружения стандартных заполнителей _1, _2и так далее. Шаблон функции bind используется is_placeholder для обнаружения заполнителей.
Экземпляры is_placeholder шаблона должны соответствовать UnaryTypeTrait требованиям. Реализация должна предоставлять определение, которое имеет базовую характеристику integral_constant<int, J> if T is the type std::placeholders::_J, в противном случае оно должно иметь базовую характеристику integral_constant<int, 0>. Программа может специализировать этот шаблон для определяемого пользователем типа, T чтобы он имел базовую характеристику integral_constant<int, N> with, N > 0 чтобы указать, что он T должен рассматриваться как тип-заполнитель.
В следующем тексте:
FD это тип decay_t<F>,
fd является l-значением типа, FD построенным из std::forward<F>(f),
Ti это ith тип в пакете параметров шаблона BoundArgs,
TDi это тип decay_t<Ti>,
ti является ith аргументом в параметре функции пакета bound_args,
tdi является l-значением типа, TDi построенным из std::forward<Ti>(ti),
Uj - jth выведенный тип UnBoundArgs&&... параметра оболочки переадресации вызовов, а
uj это jth аргумент , связанный с Uj.
template<class F, class... BoundArgs>
unspecified bind(F&& f, BoundArgs&&... bound_args);
Requires: is_constructible_v<FD, F> будет true. Для каждого Ti в BoundArgs, is_constructible_v<TDi, Ti> должно быть true. INVOKE(fd, w1, w2, …, wN) ([func.require]) Должен быть допустимым выражением для некоторых значений w1, w2, ..., wN, где N имеет значение sizeof...(bound_args). Квалификаторы cv cv оболочки вызова g, как указано ниже, не должны быть ни, volatile ни const volatile.
Returns: forwarding call wrapper g. Эффект g(u1, u2, …, uM) должен быть
INVOKE(fd, std::forward<V1>(v1), std::forward<V2>(v2), …, std::forward<VN>(vN))
где значения и типы связанных аргументов v1, v2..., vN определяются , как указано ниже. Конструктор копирования и конструктор перемещения оболочки перенаправляющего вызова должны вызывать исключение тогда и только тогда, когда соответствующий конструктор FD любого из типов TDi вызывает исключение.
Remarks: Тип возвращаемого значения должен удовлетворять требованиям MoveConstructible. Если все FD и TDi удовлетворяют требованиям CopyConstructible, то тип возвращаемого значения должен удовлетворять требованиям CopyConstructible. [ Note: Это подразумевает, что все так FD и TDi есть MoveConstructible. ] — end note
template<class R, class F, class... BoundArgs>
unspecified bind(F&& f, BoundArgs&&... bound_args);
Requires: is_constructible_v<FD, F> будет true. Для каждого Ti в BoundArgs, is_constructible_v<TDi, Ti> должно быть true. INVOKE(fd, w1, w2, …, wN) должен быть допустимым выражением для некоторых значений w1, w2, ..., wN, где N имеет значение sizeof...(bound_args). Квалификаторы cv cv оболочки вызова g, как указано ниже, не должны быть ни, volatile ни const volatile.
Returns: forwarding call wrapper g. Эффект g(u1, u2, …, uM) должен быть
INVOKE<R>(fd, std::forward<V1>(v1), std::forward<V2>(v2), …, std::forward<VN>(vN))
где значения и типы связанных аргументов v1, v2..., vN определяются , как указано ниже. Конструктор копирования и конструктор перемещения оболочки перенаправляющего вызова должны вызывать исключение тогда и только тогда, когда соответствующий конструктор FD любого из типов TDi вызывает исключение.
Remarks: Тип возвращаемого значения должен удовлетворять требованиям MoveConstructible. Если все FD и TDi удовлетворяют требованиям CopyConstructible, то тип возвращаемого значения должен удовлетворять требованиям CopyConstructible. [ Note: Это подразумевает, что все так FD и TDi есть MoveConstructible. ] — end note
Эти значения bound arguments v1, v2, ..., vN и соответствующие их типы V1, V2, ..., в VN зависимости от типов , TDi полученных от вызова bind и CV-классификаторов cv обертки вызова g следующим образом :
если TDi есть reference_wrapper<T>, аргумент равен tdi.get() и его тип Vi равен T&;
если значение is_bind_expression_v<TDi> равно true, аргумент равен tdi(std::forward<Uj>(uj)...) и его тип Vi равен invoke_result_t<TDi cv &, Uj...>&&;
если значение j в is_placeholder_v<TDi> не равен нулю, аргумент std::forward<Uj>(uj) и ее тип Vi является Uj&&;
в противном случае значение равно, tdi а его тип Vi - TDi cv &.
namespace std::placeholders { // M is the implementation-defined number of placeholders see below _1; see below _2; . . . see below _M; }
Все типы заполнителей должны быть DefaultConstructible и CopyConstructible, а их конструкторы по умолчанию и конструкторы копирования / перемещения не должны вызывать исключений. Это определяется реализацией ли типы заполнителей являются CopyAssignable. CopyAssignable Операторы присваивания копий заполнителей не должны вызывать исключений.
template<class R, class T> unspecified mem_fn(R T::* pm) noexcept;
Returns: Простой call wrapper fn такой, что выражение fn(t, a2, ..., aN) эквивалентно INVOKE(pm, t, a2, ..., aN) ([func.require]).
В этом подпункте описывается полиморфный класс-оболочка, который инкапсулирует произвольные вызываемые объекты.
Исключение типа bad_function_call выдается функциейfunction::operator() ([func.wrap.func.inv]), когда объект-оболочка функции не имеет цели.
namespace std {
class bad_function_call : public exception {
public:
// [func.wrap.badcall.const], constructor
bad_function_call() noexcept;
};
}
bad_function_call() noexcept;
namespace std { template<class> class function; // not defined 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&&); template<class F> function(F); function& operator=(const function&); function& operator=(function&&); function& operator=(nullptr_t) noexcept; template<class F> function& operator=(F&&); template<class F> function& operator=(reference_wrapper<F>) noexcept; ~function(); // [func.wrap.func.mod], function modifiers void swap(function&) noexcept; // [func.wrap.func.cap], function capacity explicit operator bool() const noexcept; // [func.wrap.func.inv], function invocation R operator()(ArgTypes...) const; // [func.wrap.func.targ], function target access const type_info& target_type() const noexcept; template<class T> T* target() noexcept; template<class T> const T* target() const noexcept; }; template<class R, class... ArgTypes> function(R(*)(ArgTypes...)) -> function<R(ArgTypes...)>; template<class F> function(F) -> function<see below>; // [func.wrap.func.nullptr], Null pointer comparisons template <class R, class... ArgTypes> bool operator==(const function<R(ArgTypes...)>&, nullptr_t) noexcept; template <class R, class... ArgTypes> bool operator==(nullptr_t, const function<R(ArgTypes...)>&) noexcept; template <class R, class... ArgTypes> bool operator!=(const function<R(ArgTypes...)>&, nullptr_t) noexcept; template <class R, class... ArgTypes> bool operator!=(nullptr_t, const function<R(ArgTypes...)>&) noexcept; // [func.wrap.func.alg], specialized algorithms template <class R, class... ArgTypes> void swap(function<R(ArgTypes...)>&, function<R(ArgTypes...)>&) noexcept; }
function Шаблон класса обеспечивает полиморфные упаковщики, обобщающие понятие указателя функции. Оболочки могут хранить, копировать и вызывать произвольные callable objects, заданные a call signature, что позволяет функциям быть первоклассными объектами.
A callable type F используется Lvalue-Callable для типов аргументов ArgTypes и типа возвращаемого значения, R если выражение INVOKE<R>(declval<F&>(), declval<ArgTypes>()...), рассматриваемое как a unevaluated operand, имеет правильный формат ([func.require]).
[ Note: Типы, определенные в руководствах по вычетам, function могут измениться в будущих версиях этого международного стандарта. ] — end note
function() noexcept;
function(nullptr_t) noexcept;
function(const function& f);
Throws: не должен генерировать исключения, если fцель является специализацией reference_wrapper или указателем на функцию. В противном случае может вызвать bad_alloc или любое исключение, созданное конструктором копирования сохраненного вызываемого объекта. [ Note: Реализациям рекомендуется избегать использования динамически выделяемой памяти для небольших вызываемых объектов, например, где fцелью является объект, содержащий только указатель или ссылку на объект и указатель на функцию-член. ] — end note
function(function&& f);
Postconditions: Если !f, *this не имеют целей; в противном случае цель *this эквивалентна цели f до построения и f находится в допустимом состоянии с неопределенным значением.
Throws: не должен генерировать исключения, если fцель является специализацией reference_wrapper или указателем на функцию. В противном случае может вызвать bad_alloc или любое исключение, созданное конструктором копирования или перемещения сохраненного вызываемого объекта. [ Note: Реализациям рекомендуется избегать использования динамически выделяемой памяти для небольших вызываемых объектов, например, где fцелью является объект, содержащий только указатель или ссылку на объект и указатель на функцию-член. ] — end note
template<class F> function(F f);
Remarks: Этот шаблон конструктора не должен участвовать в разрешении перегрузки, если только он не F предназначен Lvalue-Callable для типов аргументов ArgTypes... и типа возвращаемого значения R.
В противном случае *this нацелена на копию, f инициализированную с помощью std::move(f). [ Note: Реализациям рекомендуется избегать использования динамически выделяемой памяти для небольших вызываемых объектов, например, где f объект, содержащий только указатель или ссылку на объект и указатель на функцию-член. ] — end note
Throws: не должен генерировать исключения, если f это указатель на функцию или reference_wrapper<T> для некоторых T. В противном случае может вызвать bad_alloc или любое исключение, созданное конструктором Fкопирования или перемещения.
template<class F> function(F) -> function<see below>;
Remarks: Это руководство по выводу участвует в разрешении перегрузки только в том случае, если &F::operator() оно правильно сформировано, когда рассматривается как неоцененный операнд. В том случае, если decltype(&F::operator()) is имеет форму R(G::*)(A...) cv &opt noexceptopt для типа класса G, то выводимый тип имеет вид function<R(A...)>.
[ Example:
void f() {
int i{5};
function g = [&](double) { return i; }; // deduces function<int(double)>
}
— end example ]
function& operator=(const function& f);
function& operator=(function&& f);
function& operator=(nullptr_t) noexcept;
template<class F> function& operator=(F&& f);
Remarks: Этот оператор присваивания не должен участвовать в разрешении перегрузки, кроме decay_t<F> как Lvalue-Callable для типов аргументов ArgTypes... и типа возвращаемого значения R.
template<class F> function& operator=(reference_wrapper<F> f) noexcept;
~function();
void swap(function& other) noexcept;
explicit operator bool() const noexcept;
R operator()(ArgTypes... args) const;
Returns: INVOKE<R>(f, std::forward<ArgTypes>(args)...) ([func.require]), где f - target object оф *this.
const type_info& target_type() const noexcept;
template<class T> T* target() noexcept;
template<class T> const T* target() const noexcept;
template <class R, class... ArgTypes>
bool operator==(const function<R(ArgTypes...)>& f, nullptr_t) noexcept;
template <class R, class... ArgTypes>
bool operator==(nullptr_t, const function<R(ArgTypes...)>& f) noexcept;
template <class R, class... ArgTypes>
bool operator!=(const function<R(ArgTypes...)>& f, nullptr_t) noexcept;
template <class R, class... ArgTypes>
bool operator!=(nullptr_t, const function<R(ArgTypes...)>& f) noexcept;
template<class R, class... ArgTypes>
void swap(function<R(ArgTypes...)>& f1, function<R(ArgTypes...)>& f2) noexcept;
В этом подпункте предусмотрены function object types операции, которые ищут последовательность [pat_first, pat_last) в другой последовательности, [first, last) которая предоставляется оператору вызова функции объекта. Первая последовательность (шаблон для поиска) предоставляется конструктору объекта, а вторая (последовательность для поиска) предоставляется оператору вызова функции.
Каждая специализация шаблона класса , указанного в настоящем подпункте , [func.search] должны отвечать CopyConstructible и CopyAssignable требованиям. Параметры шаблона с именем
ForwardIterator,
ForwardIterator1,
ForwardIterator2,
RandomAccessIterator,
RandomAccessIterator1,
RandomAccessIterator2, а также
BinaryPredicate
шаблонов, указанных в этом подпункте, [func.search] должны соответствовать тем же требованиям и семантике, что и в [algorithms.general]. Названные параметры шаблона Hash должны соответствовать требованиям, указанным в [hash.requirements].
Программа поиска Бойера-Мура реализует алгоритм поиска Бойера-Мура. Программа поиска Boyer-Moore-Horspool реализует алгоритм поиска Boyer-Moore-Horspool. В общем, поисковик Бойера-Мура будет использовать больше памяти и работать лучше, чем Бойер-Мур-Хорспул.
template <class ForwardIterator1, class BinaryPredicate = equal_to<>> class default_searcher { public: default_searcher(ForwardIterator1 pat_first, ForwardIterator1 pat_last, BinaryPredicate pred = BinaryPredicate()); template <class ForwardIterator2> pair<ForwardIterator2, ForwardIterator2> operator()(ForwardIterator2 first, ForwardIterator2 last) const; private: ForwardIterator1 pat_first_; // exposition only ForwardIterator1 pat_last_; // exposition only BinaryPredicate pred_; // exposition only };
default_searcher(ForwardIterator pat_first, ForwardIterator pat_last,
BinaryPredicate pred = BinaryPredicate());
Effects: Создает default_searcher объект, инициализируясь pat_first_ с помощью pat_first, pat_last_с помощью pat_lastи pred_ с помощью pred.
Throws: Любое исключение, созданное конструктором копирования BinaryPredicate или ForwardIterator1.
template<class ForwardIterator2>
pair<ForwardIterator2, ForwardIterator2>
operator()(ForwardIterator2 first, ForwardIterator2 last) const;
template <class RandomAccessIterator1, class Hash = hash<typename iterator_traits<RandomAccessIterator1>::value_type>, class BinaryPredicate = equal_to<>> class boyer_moore_searcher { public: boyer_moore_searcher(RandomAccessIterator1 pat_first, RandomAccessIterator1 pat_last, Hash hf = Hash(), BinaryPredicate pred = BinaryPredicate()); template <class RandomAccessIterator2> pair<RandomAccessIterator2, RandomAccessIterator2> operator()(RandomAccessIterator2 first, RandomAccessIterator2 last) const; private: RandomAccessIterator1 pat_first_; // exposition only RandomAccessIterator1 pat_last_; // exposition only Hash hash_; // exposition only BinaryPredicate pred_; // exposition only };
boyer_moore_searcher(RandomAccessIterator1 pat_first,
RandomAccessIterator1 pat_last,
Hash hf = Hash(),
BinaryPredicate pred = BinaryPredicate());
Requires: Тип значения RandomAccessIterator1 должен соответствовать DefaultConstructible требованиям, CopyConstructible требованиям и CopyAssignable требованиям.
Requires: Для любых двух значений A и B типа iterator_traits<RandomAccessIterator1>::value_type, если pred(A, B) == true, то hf(A) == hf(B) должно быть true.
Effects: Создает boyer_moore_searcher объект, инициализируясь pat_first_ с pat_first, pat_last_ с pat_last, hash_ с hfи pred_ с pred.
Throws: Любое исключение брошенная копию конструктора RandomAccessIterator1, или с помощью конструктора по умолчанию, конструктор копирования или оператор присваивания копии типа ценностной RandomAccessIterator1или конструктор копирования или operator() из BinaryPredicate или Hash. Может bad_alloc вызвать ошибку, если не может быть выделена дополнительная память, необходимая для внутренних структур данных.
template <class RandomAccessIterator2>
pair<RandomAccessIterator2, RandomAccessIterator2>
operator()(RandomAccessIterator2 first, RandomAccessIterator2 last) const;
Returns: Пара итераторов i и j такие, что
i - это первый итератор в диапазоне, [first, last - (pat_last_ - pat_first_)) такой, что для каждого неотрицательного целого числа, n меньшего, чем pat_last_ - pat_first_ выполняется следующее условие:, pred(*(i + n), *(pat_first_ + n)) != falseи
j == next(i, distance(pat_first_, pat_last_)).
Возвращает, make_pair(first, first) если [pat_first_, pat_last_) пусто, в противном случае возвращает, make_pair(last, last) если такой итератор не найден.
template <class RandomAccessIterator1, class Hash = hash<typename iterator_traits<RandomAccessIterator1>::value_type>, class BinaryPredicate = equal_to<>> class boyer_moore_horspool_searcher { public: boyer_moore_horspool_searcher(RandomAccessIterator1 pat_first, RandomAccessIterator1 pat_last, Hash hf = Hash(), BinaryPredicate pred = BinaryPredicate()); template <class RandomAccessIterator2> pair<RandomAccessIterator2, RandomAccessIterator2> operator()(RandomAccessIterator2 first, RandomAccessIterator2 last) const; private: RandomAccessIterator1 pat_first_; // exposition only RandomAccessIterator1 pat_last_; // exposition only Hash hash_; // exposition only BinaryPredicate pred_; // exposition only };
boyer_moore_horspool_searcher(RandomAccessIterator1 pat_first,
RandomAccessIterator1 pat_last,
Hash hf = Hash(),
BinaryPredicate pred = BinaryPredicate());
Requires: Тип значения RandomAccessIterator1 должны удовлетворять DefaultConstructible, CopyConstructibleи CopyAssignable требования.
Requires: Для любых двух значений A и B типа iterator_traits<RandomAccessIterator1>::value_type, если pred(A, B) == true, то hf(A) == hf(B) должно быть true.
Effects: Создает boyer_moore_horspool_searcher объект, инициализируясь pat_first_ с pat_first, pat_last_ с pat_last, hash_ с hfи pred_ с pred.
Throws: Любое исключение брошенная копию конструктора RandomAccessIterator1, или с помощью конструктора по умолчанию, конструктор копирования или оператор присваивания копии типа ценностной RandomAccessIterator1 или копирующего конструктора или operator() из BinaryPredicate или Hash. Может bad_alloc вызвать ошибку, если не может быть выделена дополнительная память, необходимая для внутренних структур данных.
template <class RandomAccessIterator2>
pair<RandomAccessIterator2, RandomAccessIterator2>
operator()(RandomAccessIterator2 first, RandomAccessIterator2 last) const;
Returns: Пара итераторов i и j такие, что
i - это первый итератор i в диапазоне, [first, last - (pat_last_ - pat_first_)) такой, что для каждого неотрицательного целого числа, n меньшего, чем pat_last_ - pat_first_ выполняется следующее условие:, pred(*(i + n), *(pat_first_ + n)) != falseи
j == next(i, distance(pat_first_, pat_last_)).
Возвращает, make_pair(first, first) если [pat_first_, pat_last_) пусто, в противном случае возвращает, make_pair(last, last) если такой итератор не найден.
Неупорядоченные ассоциативные контейнеры, определенные в [unord] специализациях класса template hash ([functional.syn]) в качестве хэш-функции по умолчанию.
Каждая специализация hash включена или отключена, как описано ниже. [ Note: Включенные специализации соответствуют требованиям Hash, а отключенные - нет. ] Каждый заголовок, который объявляет шаблон, предоставляет включенные специализации для и всех cv-неквалифицированных типов арифметики, перечисления и указателя. Для любого типа, для которого ни библиотека, ни пользователь не предоставляют явную или частичную специализацию шаблона класса , отключен. — end note hash hash nullptr_t Key hashhash<Key>
Если библиотека предоставляет явную или частичную специализацию hash<Key>, эта специализация включена, если не указано иное, и ее функции-члены, noexcept если не указано иное.
Если H инвалид специализации hash, эти значения false: is_default_constructible_v<H>, is_copy_constructible_v<H>, is_move_constructible_v<H>, is_copy_assignable_v<H>, и is_move_assignable_v<H>. Инвалидов специализации hash нет function object types. [ Note: Это означает, что специализация hash существует, но любые попытки использовать ее как a Hash будут плохо сформированы. ] — end note
Включенная специализация hash<Key> :
удовлетворяют Hash requirements, с Key как тип аргумента вызова функции, то DefaultConstructible requirements, то CopyAssignable requirements,
быть swappable для lvalues,
удовлетворяют требованию, что if k1 == k2 is true, h(k1) == h(k2) is также true, where h is объект типа hash<Key> и k1 and k2 are объекты типа Key;
удовлетворять требованию, согласно которому выражение h(k), где h является объектом типа hash<Key> и k является объектом типа Key, не должно вызывать исключения, если только hash<Key> это не определенная пользователем специализация, которая зависит по крайней мере от одного определяемого пользователем типа.