Mercurial > hg > CbC > CbC_gcc
diff libstdc++-v3/include/bits/range_cmp.h @ 145:1830386684a0
gcc-9.2.0
author | anatofuz |
---|---|
date | Thu, 13 Feb 2020 11:34:05 +0900 |
parents | |
children |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/libstdc++-v3/include/bits/range_cmp.h Thu Feb 13 11:34:05 2020 +0900 @@ -0,0 +1,192 @@ +// Concept-constrained comparison implementations -*- C++ -*- + +// Copyright (C) 2019-2020 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library is free +// software; you can redistribute it and/or modify it under the +// terms of the GNU General Public License as published by the +// Free Software Foundation; either version 3, or (at your option) +// any later version. + +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// Under Section 7 of GPL version 3, you are granted additional +// permissions described in the GCC Runtime Library Exception, version +// 3.1, as published by the Free Software Foundation. + +// You should have received a copy of the GNU General Public License and +// a copy of the GCC Runtime Library Exception along with this program; +// see the files COPYING3 and COPYING.RUNTIME respectively. If not, see +// <http://www.gnu.org/licenses/>. + +/** @file bits/range_cmp.h + * This is an internal header file, included by other library headers. + * Do not attempt to use it directly. @headername{functional} + */ + +#ifndef _RANGE_CMP_H +#define _RANGE_CMP_H 1 + +#if __cplusplus > 201703L +# include <bits/move.h> +# include <concepts> + +namespace std _GLIBCXX_VISIBILITY(default) +{ +_GLIBCXX_BEGIN_NAMESPACE_VERSION + + struct __is_transparent; // not defined + + // Define std::identity here so that <iterator> and <ranges> + // don't need to include <bits/stl_function.h> to get it. + + /// [func.identity] The identity function. + struct identity + { + template<typename _Tp> + constexpr _Tp&& + operator()(_Tp&& __t) const noexcept + { return std::forward<_Tp>(__t); } + + using is_transparent = __is_transparent; + }; + +#ifdef __cpp_lib_concepts +namespace ranges +{ + namespace __detail + { + // BUILTIN-PTR-CMP(T, ==, U) + template<typename _Tp, typename _Up> + concept __eq_builtin_ptr_cmp + = requires (_Tp&& __t, _Up&& __u) { { __t == __u } -> same_as<bool>; } + && convertible_to<_Tp, const volatile void*> + && convertible_to<_Up, const volatile void*> + && (! requires(_Tp&& __t, _Up&& __u) + { operator==(std::forward<_Tp>(__t), std::forward<_Up>(__u)); } + && + ! requires(_Tp&& __t, _Up&& __u) + { std::forward<_Tp>(__t).operator==(std::forward<_Up>(__u)); }); + + // BUILTIN-PTR-CMP(T, <, U) + template<typename _Tp, typename _Up> + concept __less_builtin_ptr_cmp + = requires (_Tp&& __t, _Up&& __u) { { __t < __u } -> same_as<bool>; } + && convertible_to<_Tp, const volatile void*> + && convertible_to<_Up, const volatile void*> + && (! requires(_Tp&& __t, _Up&& __u) + { operator<(std::forward<_Tp>(__t), std::forward<_Up>(__u)); } + && ! requires(_Tp&& __t, _Up&& __u) + { std::forward<_Tp>(__t).operator<(std::forward<_Up>(__u)); }); + } // namespace __detail + + // [range.cmp] Concept-constrained comparisons + + /// ranges::equal_to function object type. + struct equal_to + { + template<typename _Tp, typename _Up> + requires equality_comparable_with<_Tp, _Up> + || __detail::__eq_builtin_ptr_cmp<_Tp, _Up> + constexpr bool + operator()(_Tp&& __t, _Up&& __u) const + noexcept(noexcept(std::declval<_Tp>() == std::declval<_Up>())) + { return std::forward<_Tp>(__t) == std::forward<_Up>(__u); } + + using is_transparent = __is_transparent; + }; + + /// ranges::not_equal_to function object type. + struct not_equal_to + { + template<typename _Tp, typename _Up> + requires equality_comparable_with<_Tp, _Up> + || __detail::__eq_builtin_ptr_cmp<_Tp, _Up> + constexpr bool + operator()(_Tp&& __t, _Up&& __u) const + noexcept(noexcept(std::declval<_Up>() == std::declval<_Tp>())) + { return !equal_to{}(std::forward<_Tp>(__t), std::forward<_Up>(__u)); } + + using is_transparent = __is_transparent; + }; + + /// ranges::less function object type. + struct less + { + template<typename _Tp, typename _Up> + requires totally_ordered_with<_Tp, _Up> + || __detail::__less_builtin_ptr_cmp<_Tp, _Up> + constexpr bool + operator()(_Tp&& __t, _Up&& __u) const + noexcept(noexcept(std::declval<_Tp>() < std::declval<_Up>())) + { + if constexpr (__detail::__less_builtin_ptr_cmp<_Tp, _Up>) + { +#ifdef __cpp_lib_is_constant_evaluated + if (std::is_constant_evaluated()) + return __t < __u; +#endif + auto __x = reinterpret_cast<__UINTPTR_TYPE__>( + static_cast<const volatile void*>(std::forward<_Tp>(__t))); + auto __y = reinterpret_cast<__UINTPTR_TYPE__>( + static_cast<const volatile void*>(std::forward<_Up>(__u))); + return __x < __y; + } + else + return std::forward<_Tp>(__t) < std::forward<_Up>(__u); + } + + using is_transparent = __is_transparent; + }; + + /// ranges::greater function object type. + struct greater + { + template<typename _Tp, typename _Up> + requires totally_ordered_with<_Tp, _Up> + || __detail::__less_builtin_ptr_cmp<_Up, _Tp> + constexpr bool + operator()(_Tp&& __t, _Up&& __u) const + noexcept(noexcept(std::declval<_Up>() < std::declval<_Tp>())) + { return less{}(std::forward<_Up>(__u), std::forward<_Tp>(__t)); } + + using is_transparent = __is_transparent; + }; + + /// ranges::greater_equal function object type. + struct greater_equal + { + template<typename _Tp, typename _Up> + requires totally_ordered_with<_Tp, _Up> + || __detail::__less_builtin_ptr_cmp<_Tp, _Up> + constexpr bool + operator()(_Tp&& __t, _Up&& __u) const + noexcept(noexcept(std::declval<_Tp>() < std::declval<_Up>())) + { return !less{}(std::forward<_Tp>(__t), std::forward<_Up>(__u)); } + + using is_transparent = __is_transparent; + }; + + /// ranges::less_equal function object type. + struct less_equal + { + template<typename _Tp, typename _Up> + requires totally_ordered_with<_Tp, _Up> + || __detail::__less_builtin_ptr_cmp<_Up, _Tp> + constexpr bool + operator()(_Tp&& __t, _Up&& __u) const + noexcept(noexcept(std::declval<_Up>() < std::declval<_Tp>())) + { return !less{}(std::forward<_Up>(__u), std::forward<_Tp>(__t)); } + + using is_transparent = __is_transparent; + }; + +} // namespace ranges +#endif // library concepts +_GLIBCXX_END_NAMESPACE_VERSION +} // namespace std +#endif // C++20 +#endif // _RANGE_CMP_H