Path: blob/main/contrib/llvm-project/libcxx/include/__functional/operations.h
35259 views
// -*- C++ -*-1//===----------------------------------------------------------------------===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//89#ifndef _LIBCPP___FUNCTIONAL_OPERATIONS_H10#define _LIBCPP___FUNCTIONAL_OPERATIONS_H1112#include <__config>13#include <__functional/binary_function.h>14#include <__functional/unary_function.h>15#include <__type_traits/desugars_to.h>16#include <__utility/forward.h>1718#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)19# pragma GCC system_header20#endif2122_LIBCPP_BEGIN_NAMESPACE_STD2324// Arithmetic operations2526#if _LIBCPP_STD_VER >= 1427template <class _Tp = void>28#else29template <class _Tp>30#endif31struct _LIBCPP_TEMPLATE_VIS plus : __binary_function<_Tp, _Tp, _Tp> {32typedef _Tp __result_type; // used by valarray33_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI _Tp operator()(const _Tp& __x, const _Tp& __y) const {34return __x + __y;35}36};37_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(plus);3839// The non-transparent std::plus specialization is only equivalent to a raw plus40// operator when we don't perform an implicit conversion when calling it.41template <class _Tp>42inline const bool __desugars_to_v<__plus_tag, plus<_Tp>, _Tp, _Tp> = true;4344template <class _Tp, class _Up>45inline const bool __desugars_to_v<__plus_tag, plus<void>, _Tp, _Up> = true;4647#if _LIBCPP_STD_VER >= 1448template <>49struct _LIBCPP_TEMPLATE_VIS plus<void> {50template <class _T1, class _T2>51_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const52noexcept(noexcept(std::forward<_T1>(__t) + std::forward<_T2>(__u))) //53-> decltype(std::forward<_T1>(__t) + std::forward<_T2>(__u)) {54return std::forward<_T1>(__t) + std::forward<_T2>(__u);55}56typedef void is_transparent;57};58#endif5960#if _LIBCPP_STD_VER >= 1461template <class _Tp = void>62#else63template <class _Tp>64#endif65struct _LIBCPP_TEMPLATE_VIS minus : __binary_function<_Tp, _Tp, _Tp> {66typedef _Tp __result_type; // used by valarray67_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI _Tp operator()(const _Tp& __x, const _Tp& __y) const {68return __x - __y;69}70};71_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(minus);7273#if _LIBCPP_STD_VER >= 1474template <>75struct _LIBCPP_TEMPLATE_VIS minus<void> {76template <class _T1, class _T2>77_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const78noexcept(noexcept(std::forward<_T1>(__t) - std::forward<_T2>(__u))) //79-> decltype(std::forward<_T1>(__t) - std::forward<_T2>(__u)) {80return std::forward<_T1>(__t) - std::forward<_T2>(__u);81}82typedef void is_transparent;83};84#endif8586#if _LIBCPP_STD_VER >= 1487template <class _Tp = void>88#else89template <class _Tp>90#endif91struct _LIBCPP_TEMPLATE_VIS multiplies : __binary_function<_Tp, _Tp, _Tp> {92typedef _Tp __result_type; // used by valarray93_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI _Tp operator()(const _Tp& __x, const _Tp& __y) const {94return __x * __y;95}96};97_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(multiplies);9899#if _LIBCPP_STD_VER >= 14100template <>101struct _LIBCPP_TEMPLATE_VIS multiplies<void> {102template <class _T1, class _T2>103_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const104noexcept(noexcept(std::forward<_T1>(__t) * std::forward<_T2>(__u))) //105-> decltype(std::forward<_T1>(__t) * std::forward<_T2>(__u)) {106return std::forward<_T1>(__t) * std::forward<_T2>(__u);107}108typedef void is_transparent;109};110#endif111112#if _LIBCPP_STD_VER >= 14113template <class _Tp = void>114#else115template <class _Tp>116#endif117struct _LIBCPP_TEMPLATE_VIS divides : __binary_function<_Tp, _Tp, _Tp> {118typedef _Tp __result_type; // used by valarray119_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI _Tp operator()(const _Tp& __x, const _Tp& __y) const {120return __x / __y;121}122};123_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(divides);124125#if _LIBCPP_STD_VER >= 14126template <>127struct _LIBCPP_TEMPLATE_VIS divides<void> {128template <class _T1, class _T2>129_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const130noexcept(noexcept(std::forward<_T1>(__t) / std::forward<_T2>(__u))) //131-> decltype(std::forward<_T1>(__t) / std::forward<_T2>(__u)) {132return std::forward<_T1>(__t) / std::forward<_T2>(__u);133}134typedef void is_transparent;135};136#endif137138#if _LIBCPP_STD_VER >= 14139template <class _Tp = void>140#else141template <class _Tp>142#endif143struct _LIBCPP_TEMPLATE_VIS modulus : __binary_function<_Tp, _Tp, _Tp> {144typedef _Tp __result_type; // used by valarray145_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI _Tp operator()(const _Tp& __x, const _Tp& __y) const {146return __x % __y;147}148};149_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(modulus);150151#if _LIBCPP_STD_VER >= 14152template <>153struct _LIBCPP_TEMPLATE_VIS modulus<void> {154template <class _T1, class _T2>155_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const156noexcept(noexcept(std::forward<_T1>(__t) % std::forward<_T2>(__u))) //157-> decltype(std::forward<_T1>(__t) % std::forward<_T2>(__u)) {158return std::forward<_T1>(__t) % std::forward<_T2>(__u);159}160typedef void is_transparent;161};162#endif163164#if _LIBCPP_STD_VER >= 14165template <class _Tp = void>166#else167template <class _Tp>168#endif169struct _LIBCPP_TEMPLATE_VIS negate : __unary_function<_Tp, _Tp> {170typedef _Tp __result_type; // used by valarray171_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI _Tp operator()(const _Tp& __x) const { return -__x; }172};173_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(negate);174175#if _LIBCPP_STD_VER >= 14176template <>177struct _LIBCPP_TEMPLATE_VIS negate<void> {178template <class _Tp>179_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_Tp&& __x) const180noexcept(noexcept(-std::forward<_Tp>(__x))) //181-> decltype(-std::forward<_Tp>(__x)) {182return -std::forward<_Tp>(__x);183}184typedef void is_transparent;185};186#endif187188// Bitwise operations189190#if _LIBCPP_STD_VER >= 14191template <class _Tp = void>192#else193template <class _Tp>194#endif195struct _LIBCPP_TEMPLATE_VIS bit_and : __binary_function<_Tp, _Tp, _Tp> {196typedef _Tp __result_type; // used by valarray197_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI _Tp operator()(const _Tp& __x, const _Tp& __y) const {198return __x & __y;199}200};201_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(bit_and);202203#if _LIBCPP_STD_VER >= 14204template <>205struct _LIBCPP_TEMPLATE_VIS bit_and<void> {206template <class _T1, class _T2>207_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const208noexcept(noexcept(std::forward<_T1>(__t) &209std::forward<_T2>(__u))) -> decltype(std::forward<_T1>(__t) & std::forward<_T2>(__u)) {210return std::forward<_T1>(__t) & std::forward<_T2>(__u);211}212typedef void is_transparent;213};214#endif215216#if _LIBCPP_STD_VER >= 14217template <class _Tp = void>218struct _LIBCPP_TEMPLATE_VIS bit_not : __unary_function<_Tp, _Tp> {219_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI _Tp operator()(const _Tp& __x) const { return ~__x; }220};221_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(bit_not);222223template <>224struct _LIBCPP_TEMPLATE_VIS bit_not<void> {225template <class _Tp>226_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_Tp&& __x) const227noexcept(noexcept(~std::forward<_Tp>(__x))) //228-> decltype(~std::forward<_Tp>(__x)) {229return ~std::forward<_Tp>(__x);230}231typedef void is_transparent;232};233#endif234235#if _LIBCPP_STD_VER >= 14236template <class _Tp = void>237#else238template <class _Tp>239#endif240struct _LIBCPP_TEMPLATE_VIS bit_or : __binary_function<_Tp, _Tp, _Tp> {241typedef _Tp __result_type; // used by valarray242_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI _Tp operator()(const _Tp& __x, const _Tp& __y) const {243return __x | __y;244}245};246_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(bit_or);247248#if _LIBCPP_STD_VER >= 14249template <>250struct _LIBCPP_TEMPLATE_VIS bit_or<void> {251template <class _T1, class _T2>252_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const253noexcept(noexcept(std::forward<_T1>(__t) | std::forward<_T2>(__u))) //254-> decltype(std::forward<_T1>(__t) | std::forward<_T2>(__u)) {255return std::forward<_T1>(__t) | std::forward<_T2>(__u);256}257typedef void is_transparent;258};259#endif260261#if _LIBCPP_STD_VER >= 14262template <class _Tp = void>263#else264template <class _Tp>265#endif266struct _LIBCPP_TEMPLATE_VIS bit_xor : __binary_function<_Tp, _Tp, _Tp> {267typedef _Tp __result_type; // used by valarray268_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI _Tp operator()(const _Tp& __x, const _Tp& __y) const {269return __x ^ __y;270}271};272_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(bit_xor);273274#if _LIBCPP_STD_VER >= 14275template <>276struct _LIBCPP_TEMPLATE_VIS bit_xor<void> {277template <class _T1, class _T2>278_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const279noexcept(noexcept(std::forward<_T1>(__t) ^ std::forward<_T2>(__u))) //280-> decltype(std::forward<_T1>(__t) ^ std::forward<_T2>(__u)) {281return std::forward<_T1>(__t) ^ std::forward<_T2>(__u);282}283typedef void is_transparent;284};285#endif286287// Comparison operations288289#if _LIBCPP_STD_VER >= 14290template <class _Tp = void>291#else292template <class _Tp>293#endif294struct _LIBCPP_TEMPLATE_VIS equal_to : __binary_function<_Tp, _Tp, bool> {295typedef bool __result_type; // used by valarray296_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI bool operator()(const _Tp& __x, const _Tp& __y) const {297return __x == __y;298}299};300_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(equal_to);301302#if _LIBCPP_STD_VER >= 14303template <>304struct _LIBCPP_TEMPLATE_VIS equal_to<void> {305template <class _T1, class _T2>306_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const307noexcept(noexcept(std::forward<_T1>(__t) == std::forward<_T2>(__u))) //308-> decltype(std::forward<_T1>(__t) == std::forward<_T2>(__u)) {309return std::forward<_T1>(__t) == std::forward<_T2>(__u);310}311typedef void is_transparent;312};313#endif314315// The non-transparent std::equal_to specialization is only equivalent to a raw equality316// comparison when we don't perform an implicit conversion when calling it.317template <class _Tp>318inline const bool __desugars_to_v<__equal_tag, equal_to<_Tp>, _Tp, _Tp> = true;319320// In the transparent case, we do not enforce that321template <class _Tp, class _Up>322inline const bool __desugars_to_v<__equal_tag, equal_to<void>, _Tp, _Up> = true;323324#if _LIBCPP_STD_VER >= 14325template <class _Tp = void>326#else327template <class _Tp>328#endif329struct _LIBCPP_TEMPLATE_VIS not_equal_to : __binary_function<_Tp, _Tp, bool> {330typedef bool __result_type; // used by valarray331_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI bool operator()(const _Tp& __x, const _Tp& __y) const {332return __x != __y;333}334};335_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(not_equal_to);336337#if _LIBCPP_STD_VER >= 14338template <>339struct _LIBCPP_TEMPLATE_VIS not_equal_to<void> {340template <class _T1, class _T2>341_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const342noexcept(noexcept(std::forward<_T1>(__t) != std::forward<_T2>(__u))) //343-> decltype(std::forward<_T1>(__t) != std::forward<_T2>(__u)) {344return std::forward<_T1>(__t) != std::forward<_T2>(__u);345}346typedef void is_transparent;347};348#endif349350#if _LIBCPP_STD_VER >= 14351template <class _Tp = void>352#else353template <class _Tp>354#endif355struct _LIBCPP_TEMPLATE_VIS less : __binary_function<_Tp, _Tp, bool> {356typedef bool __result_type; // used by valarray357_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI bool operator()(const _Tp& __x, const _Tp& __y) const {358return __x < __y;359}360};361_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(less);362363template <class _Tp>364inline const bool __desugars_to_v<__less_tag, less<_Tp>, _Tp, _Tp> = true;365366#if _LIBCPP_STD_VER >= 14367template <>368struct _LIBCPP_TEMPLATE_VIS less<void> {369template <class _T1, class _T2>370_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const371noexcept(noexcept(std::forward<_T1>(__t) < std::forward<_T2>(__u))) //372-> decltype(std::forward<_T1>(__t) < std::forward<_T2>(__u)) {373return std::forward<_T1>(__t) < std::forward<_T2>(__u);374}375typedef void is_transparent;376};377378template <class _Tp>379inline const bool __desugars_to_v<__less_tag, less<>, _Tp, _Tp> = true;380#endif381382#if _LIBCPP_STD_VER >= 14383template <class _Tp = void>384#else385template <class _Tp>386#endif387struct _LIBCPP_TEMPLATE_VIS less_equal : __binary_function<_Tp, _Tp, bool> {388typedef bool __result_type; // used by valarray389_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI bool operator()(const _Tp& __x, const _Tp& __y) const {390return __x <= __y;391}392};393_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(less_equal);394395#if _LIBCPP_STD_VER >= 14396template <>397struct _LIBCPP_TEMPLATE_VIS less_equal<void> {398template <class _T1, class _T2>399_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const400noexcept(noexcept(std::forward<_T1>(__t) <= std::forward<_T2>(__u))) //401-> decltype(std::forward<_T1>(__t) <= std::forward<_T2>(__u)) {402return std::forward<_T1>(__t) <= std::forward<_T2>(__u);403}404typedef void is_transparent;405};406#endif407408#if _LIBCPP_STD_VER >= 14409template <class _Tp = void>410#else411template <class _Tp>412#endif413struct _LIBCPP_TEMPLATE_VIS greater_equal : __binary_function<_Tp, _Tp, bool> {414typedef bool __result_type; // used by valarray415_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI bool operator()(const _Tp& __x, const _Tp& __y) const {416return __x >= __y;417}418};419_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(greater_equal);420421#if _LIBCPP_STD_VER >= 14422template <>423struct _LIBCPP_TEMPLATE_VIS greater_equal<void> {424template <class _T1, class _T2>425_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const426noexcept(noexcept(std::forward<_T1>(__t) >=427std::forward<_T2>(__u))) -> decltype(std::forward<_T1>(__t) >= std::forward<_T2>(__u)) {428return std::forward<_T1>(__t) >= std::forward<_T2>(__u);429}430typedef void is_transparent;431};432#endif433434#if _LIBCPP_STD_VER >= 14435template <class _Tp = void>436#else437template <class _Tp>438#endif439struct _LIBCPP_TEMPLATE_VIS greater : __binary_function<_Tp, _Tp, bool> {440typedef bool __result_type; // used by valarray441_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI bool operator()(const _Tp& __x, const _Tp& __y) const {442return __x > __y;443}444};445_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(greater);446447#if _LIBCPP_STD_VER >= 14448template <>449struct _LIBCPP_TEMPLATE_VIS greater<void> {450template <class _T1, class _T2>451_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const452noexcept(noexcept(std::forward<_T1>(__t) > std::forward<_T2>(__u))) //453-> decltype(std::forward<_T1>(__t) > std::forward<_T2>(__u)) {454return std::forward<_T1>(__t) > std::forward<_T2>(__u);455}456typedef void is_transparent;457};458#endif459460// Logical operations461462#if _LIBCPP_STD_VER >= 14463template <class _Tp = void>464#else465template <class _Tp>466#endif467struct _LIBCPP_TEMPLATE_VIS logical_and : __binary_function<_Tp, _Tp, bool> {468typedef bool __result_type; // used by valarray469_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI bool operator()(const _Tp& __x, const _Tp& __y) const {470return __x && __y;471}472};473_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(logical_and);474475#if _LIBCPP_STD_VER >= 14476template <>477struct _LIBCPP_TEMPLATE_VIS logical_and<void> {478template <class _T1, class _T2>479_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const480noexcept(noexcept(std::forward<_T1>(__t) && std::forward<_T2>(__u))) //481-> decltype(std::forward<_T1>(__t) && std::forward<_T2>(__u)) {482return std::forward<_T1>(__t) && std::forward<_T2>(__u);483}484typedef void is_transparent;485};486#endif487488#if _LIBCPP_STD_VER >= 14489template <class _Tp = void>490#else491template <class _Tp>492#endif493struct _LIBCPP_TEMPLATE_VIS logical_not : __unary_function<_Tp, bool> {494typedef bool __result_type; // used by valarray495_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI bool operator()(const _Tp& __x) const { return !__x; }496};497_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(logical_not);498499#if _LIBCPP_STD_VER >= 14500template <>501struct _LIBCPP_TEMPLATE_VIS logical_not<void> {502template <class _Tp>503_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_Tp&& __x) const504noexcept(noexcept(!std::forward<_Tp>(__x))) //505-> decltype(!std::forward<_Tp>(__x)) {506return !std::forward<_Tp>(__x);507}508typedef void is_transparent;509};510#endif511512#if _LIBCPP_STD_VER >= 14513template <class _Tp = void>514#else515template <class _Tp>516#endif517struct _LIBCPP_TEMPLATE_VIS logical_or : __binary_function<_Tp, _Tp, bool> {518typedef bool __result_type; // used by valarray519_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI bool operator()(const _Tp& __x, const _Tp& __y) const {520return __x || __y;521}522};523_LIBCPP_CTAD_SUPPORTED_FOR_TYPE(logical_or);524525#if _LIBCPP_STD_VER >= 14526template <>527struct _LIBCPP_TEMPLATE_VIS logical_or<void> {528template <class _T1, class _T2>529_LIBCPP_CONSTEXPR_SINCE_CXX14 _LIBCPP_HIDE_FROM_ABI auto operator()(_T1&& __t, _T2&& __u) const530noexcept(noexcept(std::forward<_T1>(__t) || std::forward<_T2>(__u))) //531-> decltype(std::forward<_T1>(__t) || std::forward<_T2>(__u)) {532return std::forward<_T1>(__t) || std::forward<_T2>(__u);533}534typedef void is_transparent;535};536#endif537538_LIBCPP_END_NAMESPACE_STD539540#endif // _LIBCPP___FUNCTIONAL_OPERATIONS_H541542543