[PATCH] Re-implement predefined operators
François Dumont
frs.dumont@gmail.com
Mon Oct 7 17:11:35 GMT 2024
Same version but this time I can confirm that I've run all testsuite in
C++98 and default -std modes x64 Linux.
François
On 25/09/2024 06:59, François Dumont wrote:
> Here is a refreshed version due to a conflict with recent changes.
>
> François
>
>
> On 07/08/2024 15:39, François Dumont wrote:
>> Hi
>>
>> For recall and updated patch following latest algo changes. I've also
>> limited my changes to make the patch smaller.
>>
>> François
>>
>>
>> On 05/06/2024 18:56, François Dumont wrote:
>>> Hi
>>>
>>> With the recent fixes to std::vector implementation all
>>> 23_containers and 25_algorithms tests are passing in C++98 and C++20
>>> modes.
>>>
>>> libstdc++: Reimplement __gnu_cxx::__ops operators
>>>
>>> Replace functors using iterators as input to adopt functors that are
>>> matching the same Standard expectations as the ones imposed on
>>> functor-aware
>>> algos. It forces to have iterators dereferenced at algo level and
>>> not in the
>>> predefined functors anymore.
>>>
>>> Also make sure that in algos implementation details functors are
>>> passed by
>>> reference rather than by copy.
>>>
>>> libstdc++-v3/ChangeLog:
>>>
>>> * include/bits/move.h
>>> (_GLIBCXX_FWDREF): Now substituted by a lvalue-reference in
>>> pre-c++11 mode.
>>> (_GLIBCXX_FWDCREF): New macro, substituted by a const lvalue
>>> reference in
>>> pre-c++11 mode.
>>> * include/bits/stl_tree.h: Replace _GLIBCXX_FWDREF usage by
>>> _GLIBCXX_FWDCREF.
>>> * include/std/functional: Include predefined_ops.h.
>>> (_Not_fn): Move to...
>>> * include/bits/predefined_ops.h: ...here, and expose a version
>>> in pre-C++14 mode.
>>> (__not_fn): New, use latter.
>>> (_Iter_less_iter, _Iter_less_val, _Val_less_iter,
>>> _Iter_equal_to_iter)
>>> (_Iter_equal_to_val, _Iter_comp_iter, _Iter_comp_val,
>>> _Val_comp_iter)
>>> (_Iter_equals_val, _Iter_equals_iter, _Iter_pred,
>>> _Iter_comp_val)
>>> (_Iter_comp_to_val, _Iter_comp_to_iter, _Iter_negate): Remove.
>>> (__iter_less_iter, __iter_less_val, __iter_comp_val,
>>> __val_less_iter)
>>> (__val_comp_iter, __iter_equal_to_iter, __iter_equal_to_val,
>>> __iter_comp_iter)
>>> (__val_comp_iter, __iter_equals_val, __iter_comp_iter,
>>> __pred_iter): Remove.
>>> (_Less, _Equal_to, _Equal_to_val, _Comp_val): New.
>>> (__less, __equal_to, __comp_val): New.
>>> * include/bits/stl_algo.h: Adapt all algos to use new
>>> __gnu_cxx::__ops operators.
>>> When possible use std::move to pass predicates between
>>> routines.
>>> * include/bits/stl_algobase.h: Likewise.
>>> * include/bits/stl_heap.h: Likewise.
>>> * include/std/deque: Cleanup usage of __gnu_cxx::__ops
>>> operators. Replace usage of
>>> std::ref by std::move to pass predicate to std::__remove_if.
>>> * include/std/string: Likewise.
>>> * include/std/vector: Likewise.
>>> * src/c++17/memory_resource.cc: Include <functional>.
>>>
>>> I'm not proud of the _GLIBCXX_FWDCREF but I'm sure you'll find a
>>> better name !
>>>
>>> Ok to commit once I've completed the test coverage ?
>>>
>>> François
-------------- next part --------------
diff --git a/libstdc++-v3/include/bits/move.h b/libstdc++-v3/include/bits/move.h
index 8397a01b632..3300f0dcf9f 100644
--- a/libstdc++-v3/include/bits/move.h
+++ b/libstdc++-v3/include/bits/move.h
@@ -182,10 +182,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
/// @} group utilities
#define _GLIBCXX_FWDREF(_Tp) _Tp&&
+#define _GLIBCXX_FWDCREF(_Tp) _Tp&&
#define _GLIBCXX_MOVE(__val) std::move(__val)
#define _GLIBCXX_FORWARD(_Tp, __val) std::forward<_Tp>(__val)
#else
-#define _GLIBCXX_FWDREF(_Tp) const _Tp&
+#define _GLIBCXX_FWDREF(_Tp) _Tp&
+#define _GLIBCXX_FWDCREF(_Tp) const _Tp&
#define _GLIBCXX_MOVE(__val) (__val)
#define _GLIBCXX_FORWARD(_Tp, __val) (__val)
#endif
diff --git a/libstdc++-v3/include/bits/predefined_ops.h b/libstdc++-v3/include/bits/predefined_ops.h
index f72d511210a..cb9017b6840 100644
--- a/libstdc++-v3/include/bits/predefined_ops.h
+++ b/libstdc++-v3/include/bits/predefined_ops.h
@@ -31,377 +31,523 @@
#define _GLIBCXX_PREDEFINED_OPS_H 1
#include <bits/move.h>
+#include <bits/stl_iterator_base_types.h>
+
+#if __cplusplus >= 201103L
+# include <bits/invoke.h>
+#endif
namespace __gnu_cxx
{
namespace __ops
{
- struct _Iter_less_iter
+#if __cplusplus >= 201103L
+ struct _Less
{
- template<typename _Iterator1, typename _Iterator2>
+ template<typename _Lhs, typename _Rhs>
_GLIBCXX14_CONSTEXPR
bool
- operator()(_Iterator1 __it1, _Iterator2 __it2) const
- { return *__it1 < *__it2; }
+ operator()(_Lhs&& __lhs, _Rhs&& __rhs) const
+ noexcept( noexcept(__lhs < __rhs) )
+ { return __lhs < __rhs; }
};
+#else
+ template<typename _Ref1, typename _Ref2>
+ struct _LessRefs
+ {
+ bool
+ operator()(_Ref1 __lhs, _Ref2 __rhs) const
+ { return __lhs < __rhs; }
- _GLIBCXX14_CONSTEXPR
- inline _Iter_less_iter
- __iter_less_iter()
- { return _Iter_less_iter(); }
+ bool
+ operator()(_Ref2 __lhs, _Ref1 __rhs) const
+ { return __lhs < __rhs; }
- struct _Iter_less_val
- {
-#if __cplusplus >= 201103L
- constexpr _Iter_less_val() = default;
-#else
- _Iter_less_val() { }
-#endif
+ bool
+ operator()(_Ref1 __lhs, _Ref1 __rhs) const
+ { return __lhs < __rhs; }
- _GLIBCXX20_CONSTEXPR
- explicit
- _Iter_less_val(_Iter_less_iter) { }
+ bool
+ operator()(_Ref2 __lhs, _Ref2 __rhs) const
+ { return __lhs < __rhs; }
+ };
- template<typename _Iterator, typename _Value>
- _GLIBCXX20_CONSTEXPR
+ template<typename _Ref>
+ struct _LessRefs<_Ref, _Ref>
+ {
bool
- operator()(_Iterator __it, _Value& __val) const
- { return *__it < __val; }
- };
+ operator()(_Ref __lhs, _Ref __rhs) const
+ { return __lhs < __rhs; }
+ };
- _GLIBCXX20_CONSTEXPR
- inline _Iter_less_val
- __iter_less_val()
- { return _Iter_less_val(); }
+ template<typename _Ite1, typename _Ite2>
+ struct _Less
+ : _LessRefs<typename std::iterator_traits<_Ite1>::reference,
+ typename std::iterator_traits<_Ite2>::reference>
+ { };
+
+ template<typename _Ite>
+ struct _LessCRef
+ : _LessRefs<typename std::iterator_traits<_Ite>::reference,
+ const typename std::iterator_traits<_Ite>::value_type&>
+ { };
+#endif
- _GLIBCXX20_CONSTEXPR
- inline _Iter_less_val
- __iter_comp_val(_Iter_less_iter)
- { return _Iter_less_val(); }
+#if __cplusplus >= 201103L
+ template<typename _Ite1, typename _Ite2>
+ constexpr _Less
+ __less(_Ite1, _Ite2) noexcept
+ { return _Less{}; }
+
+ constexpr _Less
+ __less() noexcept
+ { return _Less{}; }
+#else
+ template<typename _Ite1, typename _Ite2>
+ inline _Less<_Ite1, _Ite2>
+ __less(_Ite1, _Ite2)
+ { return _Less<_Ite1, _Ite2>(); }
+#endif
- struct _Val_less_iter
- {
#if __cplusplus >= 201103L
- constexpr _Val_less_iter() = default;
+ template<typename _Ite>
+ constexpr _Less
+ __less(_Ite) noexcept
+ { return _Less{}; }
#else
- _Val_less_iter() { }
+ template<typename _Ite>
+ inline _LessCRef<_Ite>
+ __less(_Ite)
+ { return _LessCRef<_Ite>(); }
#endif
- _GLIBCXX20_CONSTEXPR
- explicit
- _Val_less_iter(_Iter_less_iter) { }
+#if __cplusplus >= 201103L
+ template<typename _Comp, typename _Ite1, typename _Ite2>
+ constexpr _Comp&&
+ __less(_Comp&& __comp, _Ite1, _Ite2) noexcept
+ { return std::forward<_Comp>(__comp); }
+#else
+ template<typename _Comp, typename _Ite1, typename _Ite2>
+ inline _Comp
+ __less(_Comp __comp, _Ite1, _Ite2)
+ { return __comp; }
+
+ template<typename _LessRef1, typename _LessRef2, typename _Ite1, typename _Ite2>
+ inline _Less<_Ite1, _Ite2>
+ __less(const _LessRefs<_LessRef1, _LessRef2>&, _Ite1, _Ite2)
+ { return _Less<_Ite1, _Ite2>(); }
+#endif
- template<typename _Value, typename _Iterator>
- _GLIBCXX20_CONSTEXPR
- bool
- operator()(_Value& __val, _Iterator __it) const
- { return __val < *__it; }
- };
+#if __cplusplus < 201103L
+ template<typename _Ite, typename _Val>
+ struct _LessVal : _LessRefs<typename std::iterator_traits<_Ite>::reference,
+ _Val&>
+ { };
+#endif
- _GLIBCXX20_CONSTEXPR
- inline _Val_less_iter
- __val_less_iter()
- { return _Val_less_iter(); }
+#if __cplusplus >= 201103L
+ template<typename _Ite, typename _Val>
+ constexpr _Less
+ __less_val(_Ite, _Val&&) noexcept
+ { return _Less{}; }
+#else
+ template<typename _Ite, typename _Val>
+ inline _LessVal<_Ite, _Val>
+ __less_val(_Ite, _Val&)
+ { return _LessVal<_Ite, _Val>(); }
+#endif
- _GLIBCXX20_CONSTEXPR
- inline _Val_less_iter
- __val_comp_iter(_Iter_less_iter)
- { return _Val_less_iter(); }
+#if __cplusplus >= 201103L
+ template<typename _Comp, typename _Ite, typename _Val>
+ constexpr _Comp&&
+ __less_val(_Comp&& __comp, _Ite, _Val&&) noexcept
+ { return std::forward<_Comp>(__comp); }
+#else
+ template<typename _Comp, typename _Ite, typename _Val>
+ inline _Comp
+ __less_val(_Comp __comp, _Ite, _Val&)
+ { return __comp; }
+
+ template<typename _Ref1, typename _Ref2, typename _Ite, typename _Val>
+ inline _LessVal<_Ite, _Val>
+ __less_val(const _LessRefs<_Ref1, _Ref2>&, _Ite, _Val&)
+ { return _LessVal<_Ite, _Val>(); }
+#endif
- struct _Iter_equal_to_iter
+#if __cplusplus >= 201103L
+ struct _EqualTo
{
- template<typename _Iterator1, typename _Iterator2>
+ template<typename _Lhs, typename _Rhs>
_GLIBCXX20_CONSTEXPR
bool
- operator()(_Iterator1 __it1, _Iterator2 __it2) const
- { return *__it1 == *__it2; }
+ operator()(_Lhs&& __lhs, _Rhs&& __rhs) const
+ noexcept( noexcept(__lhs == __rhs) )
+ { return __lhs == __rhs; }
};
-
- _GLIBCXX20_CONSTEXPR
- inline _Iter_equal_to_iter
- __iter_equal_to_iter()
- { return _Iter_equal_to_iter(); }
-
- struct _Iter_equal_to_val
- {
- template<typename _Iterator, typename _Value>
- _GLIBCXX20_CONSTEXPR
+#else
+ template<typename _Ref1, typename _Ref2>
+ struct _EqualToRefs
+ {
bool
- operator()(_Iterator __it, _Value& __val) const
- { return *__it == __val; }
- };
-
- _GLIBCXX20_CONSTEXPR
- inline _Iter_equal_to_val
- __iter_equal_to_val()
- { return _Iter_equal_to_val(); }
-
- _GLIBCXX20_CONSTEXPR
- inline _Iter_equal_to_val
- __iter_comp_val(_Iter_equal_to_iter)
- { return _Iter_equal_to_val(); }
+ operator()(_Ref1 __lhs, _Ref2 __rhs) const
+ { return __lhs == __rhs; }
- template<typename _Compare>
- struct _Iter_comp_iter
- {
- _Compare _M_comp;
+ bool
+ operator()(_Ref2 __lhs, _Ref1 __rhs) const
+ { return __lhs == __rhs; }
- explicit _GLIBCXX14_CONSTEXPR
- _Iter_comp_iter(_Compare __comp)
- : _M_comp(_GLIBCXX_MOVE(__comp))
- { }
+ bool
+ operator()(_Ref1 __lhs, _Ref1 __rhs) const
+ { return __lhs == __rhs; }
- template<typename _Iterator1, typename _Iterator2>
- _GLIBCXX14_CONSTEXPR
- bool
- operator()(_Iterator1 __it1, _Iterator2 __it2)
- { return bool(_M_comp(*__it1, *__it2)); }
+ bool
+ operator()(_Ref2 __lhs, _Ref2 __rhs) const
+ { return __lhs == __rhs; }
};
- template<typename _Compare>
- _GLIBCXX14_CONSTEXPR
- inline _Iter_comp_iter<_Compare>
- __iter_comp_iter(_Compare __comp)
- { return _Iter_comp_iter<_Compare>(_GLIBCXX_MOVE(__comp)); }
-
- template<typename _Compare>
- struct _Iter_comp_val
+ template<typename _Ref>
+ struct _EqualToRefs<_Ref, _Ref>
{
- _Compare _M_comp;
-
- _GLIBCXX20_CONSTEXPR
- explicit
- _Iter_comp_val(_Compare __comp)
- : _M_comp(_GLIBCXX_MOVE(__comp))
- { }
+ bool
+ operator()(_Ref __lhs, _Ref __rhs) const
+ { return __lhs == __rhs; }
+ };
- _GLIBCXX20_CONSTEXPR
- explicit
- _Iter_comp_val(const _Iter_comp_iter<_Compare>& __comp)
- : _M_comp(__comp._M_comp)
- { }
+ template<typename _Ite1, typename _Ite2>
+ struct _EqualTo
+ : _EqualToRefs<typename std::iterator_traits<_Ite1>::reference,
+ typename std::iterator_traits<_Ite2>::reference>
+ { };
+#endif
#if __cplusplus >= 201103L
- _GLIBCXX20_CONSTEXPR
- explicit
- _Iter_comp_val(_Iter_comp_iter<_Compare>&& __comp)
- : _M_comp(std::move(__comp._M_comp))
- { }
+ template<typename _Ite1, typename _Ite2>
+ constexpr _EqualTo
+ __equal_to(_Ite1, _Ite2) noexcept
+ { return _EqualTo{}; }
+
+ constexpr _EqualTo
+ __equal_to() noexcept
+ { return _EqualTo{}; }
+#else
+ template<typename _Ite1, typename _Ite2>
+ inline _EqualTo<_Ite1, _Ite2>
+ __equal_to(_Ite1, _Ite2)
+ { return _EqualTo<_Ite1, _Ite2>(); }
#endif
- template<typename _Iterator, typename _Value>
- _GLIBCXX20_CONSTEXPR
- bool
- operator()(_Iterator __it, _Value& __val)
- { return bool(_M_comp(*__it, __val)); }
- };
-
- template<typename _Compare>
- _GLIBCXX20_CONSTEXPR
- inline _Iter_comp_val<_Compare>
- __iter_comp_val(_Compare __comp)
- { return _Iter_comp_val<_Compare>(_GLIBCXX_MOVE(__comp)); }
-
- template<typename _Compare>
- _GLIBCXX20_CONSTEXPR
- inline _Iter_comp_val<_Compare>
- __iter_comp_val(_Iter_comp_iter<_Compare> __comp)
- { return _Iter_comp_val<_Compare>(_GLIBCXX_MOVE(__comp)); }
-
- template<typename _Compare>
- struct _Val_comp_iter
- {
- _Compare _M_comp;
-
- _GLIBCXX20_CONSTEXPR
- explicit
- _Val_comp_iter(_Compare __comp)
- : _M_comp(_GLIBCXX_MOVE(__comp))
- { }
-
- _GLIBCXX20_CONSTEXPR
- explicit
- _Val_comp_iter(const _Iter_comp_iter<_Compare>& __comp)
- : _M_comp(__comp._M_comp)
- { }
-
#if __cplusplus >= 201103L
- _GLIBCXX20_CONSTEXPR
- explicit
- _Val_comp_iter(_Iter_comp_iter<_Compare>&& __comp)
- : _M_comp(std::move(__comp._M_comp))
- { }
+ template<typename _Ite>
+ constexpr _EqualTo
+ __equal_to(_Ite) noexcept
+ { return _EqualTo{}; }
+#else
+ template<typename _Ite>
+ inline _EqualTo<_Ite, _Ite>
+ __equal_to(_Ite)
+ { return _EqualTo<_Ite, _Ite>(); }
#endif
- template<typename _Value, typename _Iterator>
- _GLIBCXX20_CONSTEXPR
- bool
- operator()(_Value& __val, _Iterator __it)
- { return bool(_M_comp(__val, *__it)); }
- };
-
- template<typename _Compare>
- _GLIBCXX20_CONSTEXPR
- inline _Val_comp_iter<_Compare>
- __val_comp_iter(_Compare __comp)
- { return _Val_comp_iter<_Compare>(_GLIBCXX_MOVE(__comp)); }
+#if __cplusplus < 201103L
+ template<typename _Ite, typename _Val>
+ struct _EqualToVal
+ : _EqualToRefs<typename std::iterator_traits<_Ite>::reference, _Val&>
+ { };
+#endif
- template<typename _Compare>
- _GLIBCXX20_CONSTEXPR
- inline _Val_comp_iter<_Compare>
- __val_comp_iter(_Iter_comp_iter<_Compare> __comp)
- { return _Val_comp_iter<_Compare>(_GLIBCXX_MOVE(__comp)); }
+#if __cplusplus >= 201103L
+ template<typename _Comp, typename _Ite, typename _Val>
+ constexpr _Comp&&
+ __equal_to_val(_Comp&& __comp, _Ite, _Val&&) noexcept
+ { return std::forward<_Comp>(__comp); }
+#else
+ template<typename _Comp, typename _Ite, typename _Val>
+ inline _Comp
+ __equal_to_val(_Comp __comp, _Ite, _Val&)
+ { return __comp; }
+
+ template<typename _Ref1, typename _Ref2, typename _Ite, typename _Val>
+ inline _EqualToVal<_Ite, _Val>
+ __equal_to_val(const _EqualToRefs<_Ref1, _Ref2>&, _Ite, _Val&)
+ { return _EqualToVal<_Ite, _Val>(); }
+#endif
- template<typename _Value>
- struct _Iter_equals_val
+#if __cplusplus >= 201103L
+ template<typename _Val>
+ struct _EqualVal
{
- _Value& _M_value;
+ private:
+ _Val _M_val;
- _GLIBCXX20_CONSTEXPR
- explicit
- _Iter_equals_val(_Value& __value)
- : _M_value(__value)
- { }
+ public:
+ constexpr
+ _EqualVal(_Val __val)
+ : _M_val(__val) { }
- template<typename _Iterator>
+ template<typename _Lhs>
_GLIBCXX20_CONSTEXPR
bool
- operator()(_Iterator __it)
- { return *__it == _M_value; }
+ operator()(_Lhs&& __lhs) const
+ noexcept( noexcept(__lhs == _M_val) )
+ { return __lhs == _M_val; }
};
-
- template<typename _Value>
- _GLIBCXX20_CONSTEXPR
- inline _Iter_equals_val<_Value>
- __iter_equals_val(_Value& __val)
- { return _Iter_equals_val<_Value>(__val); }
-
- template<typename _Iterator1>
- struct _Iter_equals_iter
+#else
+ template<typename _Ref, typename _Val>
+ struct _EqualValRef
{
- _Iterator1 _M_it1;
+ private:
+ _Val _M_val;
- _GLIBCXX20_CONSTEXPR
- explicit
- _Iter_equals_iter(_Iterator1 __it1)
- : _M_it1(__it1)
+ public:
+ _EqualValRef(_Val __val)
+ : _M_val(__val)
{ }
- template<typename _Iterator2>
- _GLIBCXX20_CONSTEXPR
- bool
- operator()(_Iterator2 __it2)
- { return *__it2 == *_M_it1; }
+ bool
+ operator()(_Ref __lhs) const
+ { return __lhs == _M_val; }
};
- template<typename _Iterator>
- _GLIBCXX20_CONSTEXPR
- inline _Iter_equals_iter<_Iterator>
- __iter_comp_iter(_Iter_equal_to_iter, _Iterator __it)
- { return _Iter_equals_iter<_Iterator>(__it); }
-
- template<typename _Predicate>
- struct _Iter_pred
+ template<typename _Ite, typename _Val>
+ struct _EqualVal
+ : _EqualValRef<typename std::iterator_traits<_Ite>::reference, _Val>
{
- _Predicate _M_pred;
+ typedef
+ _EqualValRef<typename std::iterator_traits<_Ite>::reference, _Val> _Base;
- _GLIBCXX20_CONSTEXPR
- explicit
- _Iter_pred(_Predicate __pred)
- : _M_pred(_GLIBCXX_MOVE(__pred))
+ _EqualVal(_Val __val)
+ : _Base(__val)
{ }
-
- template<typename _Iterator>
- _GLIBCXX20_CONSTEXPR
- bool
- operator()(_Iterator __it)
- { return bool(_M_pred(*__it)); }
};
+#endif
- template<typename _Predicate>
- _GLIBCXX20_CONSTEXPR
- inline _Iter_pred<_Predicate>
- __pred_iter(_Predicate __pred)
- { return _Iter_pred<_Predicate>(_GLIBCXX_MOVE(__pred)); }
+#if __cplusplus >= 201103L
+ template<typename _Ite, typename _Val>
+ constexpr _EqualVal<const _Val&>
+ __equal_val(_Ite, const _Val& __val) noexcept
+ {return _EqualVal<const _Val&>(__val);}
+
+ template<typename _Val>
+ constexpr _EqualVal<const _Val&>
+ __equal_val(const _Val& __val) noexcept
+ {return _EqualVal<const _Val&>(__val);}
+#else
+ template<typename _Ite, typename _Val>
+ inline _EqualVal<_Ite, const _Val&>
+ __equal_val(_Ite, const _Val& __val)
+ { return _EqualVal<_Ite, const _Val&>(__val); }
+#endif
- template<typename _Compare, typename _Value>
- struct _Iter_comp_to_val
+#if __cplusplus >= 201103L
+ template<typename _BinaryPred, typename _Val>
+ struct _CompVal
{
- _Compare _M_comp;
- _Value& _M_value;
-
- _GLIBCXX20_CONSTEXPR
- _Iter_comp_to_val(_Compare __comp, _Value& __value)
- : _M_comp(_GLIBCXX_MOVE(__comp)), _M_value(__value)
+ template<typename _BPred>
+ constexpr
+ _CompVal(_BPred&& __pred, _Val __val)
+ : _M_binary_pred(std::forward<_BPred>(__pred))
+ , _M_val(__val)
+ { }
+
+ _CompVal(const _CompVal&) = default;
+ _CompVal(_CompVal&&) = default;
+ ~_CompVal() = default;
+
+ // Macro to define operator() with given cv-qualifiers ref-qualifiers,
+ // forwarding _M_binary_pred and the function arguments with the same
+ // qualifiers, and deducing the return type and exception-specification.
+# define _GLIBCXX_BINARY_PRED_CALL_OP( _QUALS ) \
+ template<typename _Arg, \
+ typename = std::__enable_if_t<std::__is_invocable< \
+ _BinaryPred _QUALS, _Arg, _Val>::value>> \
+ _GLIBCXX20_CONSTEXPR \
+ bool \
+ operator()(_Arg&& __arg) _QUALS \
+ noexcept(std::__is_nothrow_invocable< \
+ _BinaryPred _QUALS, _Arg, _Val>::value) \
+ { \
+ return std::__invoke( \
+ std::forward< _BinaryPred _QUALS >(_M_binary_pred), \
+ std::forward<_Arg>(__arg), _M_val); \
+ } \
+ \
+ template<typename _Arg, \
+ typename = std::__enable_if_t<!std::__is_invocable< \
+ _BinaryPred _QUALS, _Arg, _Val>::value>> \
+ void operator()(_Arg&&) _QUALS = delete;
+
+ _GLIBCXX_BINARY_PRED_CALL_OP( & )
+ _GLIBCXX_BINARY_PRED_CALL_OP( const & )
+ _GLIBCXX_BINARY_PRED_CALL_OP( && )
+ _GLIBCXX_BINARY_PRED_CALL_OP( const && )
+# undef _GLIBCXX_BINARY_PRED_CALL_OP
+#else
+ template<typename _BinaryPred, typename _Ite, typename _Val>
+ struct _CompVal
+ {
+ _CompVal(_BinaryPred __pred, _Val __val)
+ : _M_binary_pred(__pred), _M_val(__val)
{ }
- template<typename _Iterator>
- _GLIBCXX20_CONSTEXPR
- bool
- operator()(_Iterator __it)
- { return bool(_M_comp(*__it, _M_value)); }
+ bool
+ operator()(typename std::iterator_traits<_Ite>::reference __lhs)
+ { return bool(_M_binary_pred(__lhs, _M_val)); }
+#endif
+
+ private:
+ _BinaryPred _M_binary_pred;
+ _Val _M_val;
};
- template<typename _Compare, typename _Value>
- _Iter_comp_to_val<_Compare, _Value>
- _GLIBCXX20_CONSTEXPR
- __iter_comp_val(_Compare __comp, _Value &__val)
+#if __cplusplus >= 201103L
+ template<typename _BPred, typename _Ite, typename _Val>
+ _GLIBCXX20_CONSTEXPR inline
+ _CompVal<std::__decay_t<_BPred>, const _Val&>
+ __comp_val(_BPred&& __pred, _Ite, const _Val& __val)
+ noexcept(std::is_nothrow_constructible<std::__decay_t<_BPred>,
+ _BPred&&>::value)
{
- return _Iter_comp_to_val<_Compare, _Value>(_GLIBCXX_MOVE(__comp), __val);
+ return
+ _CompVal<std::__decay_t<_BPred>, const _Val&>
+ (std::forward<_BPred>(__pred), __val);
}
+#else
+ template<typename _BPred, typename _Ite, typename _Val>
+ inline _CompVal<_BPred, _Ite, const _Val&>
+ __comp_val(_BPred __pred, _Ite, const _Val& __val)
+ { return _CompVal<_BPred, _Ite, const _Val&>(__pred, __val); }
+#endif
- template<typename _Compare, typename _Iterator1>
- struct _Iter_comp_to_iter
+#if __cplusplus >= 201103L
+ template<typename _BPred, typename _InIte, typename _Ite>
+ _GLIBCXX20_CONSTEXPR inline
+ _CompVal<std::__decay_t<_BPred>,
+ typename std::iterator_traits<_Ite>::reference>
+ __equal_ite(_BPred&& __pred, _InIte, _Ite __ite)
+ noexcept(std::is_nothrow_constructible<std::__decay_t<_BPred>,
+ _BPred&&>::value)
{
- _Compare _M_comp;
- _Iterator1 _M_it1;
-
- _GLIBCXX20_CONSTEXPR
- _Iter_comp_to_iter(_Compare __comp, _Iterator1 __it1)
- : _M_comp(_GLIBCXX_MOVE(__comp)), _M_it1(__it1)
- { }
-
- template<typename _Iterator2>
- _GLIBCXX20_CONSTEXPR
- bool
- operator()(_Iterator2 __it2)
- { return bool(_M_comp(*__it2, *_M_it1)); }
- };
+ return
+ _CompVal<std::__decay_t<_BPred>,
+ typename std::iterator_traits<_Ite>::reference>
+ (std::forward<_BPred>(__pred), *__ite);
+ }
- template<typename _Compare, typename _Iterator>
- _GLIBCXX20_CONSTEXPR
- inline _Iter_comp_to_iter<_Compare, _Iterator>
- __iter_comp_iter(_Iter_comp_iter<_Compare> __comp, _Iterator __it)
+ template<typename _InIte, typename _Ite>
+ _GLIBCXX20_CONSTEXPR inline
+ _EqualVal<typename std::iterator_traits<_Ite>::reference>
+ __equal_ite(_EqualTo, _InIte, _Ite __ite)
{
- return _Iter_comp_to_iter<_Compare, _Iterator>(
- _GLIBCXX_MOVE(__comp._M_comp), __it);
+ return
+ _EqualVal<typename std::iterator_traits<_Ite>::reference>(*__ite);
+ }
+#else
+ template<typename _BPred, typename _InIte, typename _Ite>
+ inline
+ _CompVal<_BPred, _InIte, typename std::iterator_traits<_Ite>::reference>
+ __equal_ite(_BPred __pred, _InIte, _Ite __ite)
+ {
+ return
+ _CompVal<_BPred, _InIte, typename std::iterator_traits<_Ite>::reference>
+ (__pred, *__ite);
}
- template<typename _Predicate>
- struct _Iter_negate
+ template<typename _Ref1, typename _Ref2, typename _InIte, typename _Ite>
+ inline
+ _EqualVal<_InIte, typename std::iterator_traits<_Ite>::reference>
+ __equal_ite(const _EqualToRefs<_Ref1, _Ref2>&, _InIte, _Ite __ite)
{
- _Predicate _M_pred;
+ return
+ _EqualVal<_InIte, typename std::iterator_traits<_Ite>::reference>
+ (*__ite);
+ }
+#endif
+} // namespace __ops
+} // namespace __gnu_cxx
- _GLIBCXX20_CONSTEXPR
- explicit
- _Iter_negate(_Predicate __pred)
- : _M_pred(_GLIBCXX_MOVE(__pred))
- { }
- template<typename _Iterator>
- _GLIBCXX20_CONSTEXPR
- bool
- operator()(_Iterator __it)
- { return !bool(_M_pred(*__it)); }
+namespace std _GLIBCXX_VISIBILITY(default)
+{
+_GLIBCXX_BEGIN_NAMESPACE_VERSION
+
+#if __cplusplus >= 201103L
+ /// Generalized negator.
+ template<typename _Fn>
+ class _Not_fn
+ {
+ template<typename _Fn2, typename... _Args>
+ using __inv_res_t = typename __invoke_result<_Fn2, _Args...>::type;
+
+ template<typename _Tp>
+ static decltype(!std::declval<_Tp>())
+ _S_not() noexcept(noexcept(!std::declval<_Tp>()));
+
+ public:
+ template<typename _Fn2>
+ constexpr
+ _Not_fn(_Fn2&& __fn, int)
+ : _M_fn(std::forward<_Fn2>(__fn)) { }
+
+ _Not_fn(const _Not_fn& __fn) = default;
+ _Not_fn(_Not_fn&& __fn) = default;
+ ~_Not_fn() = default;
+
+ // Macro to define operator() with given cv-qualifiers ref-qualifiers,
+ // forwarding _M_fn and the function arguments with the same qualifiers,
+ // and deducing the return type and exception-specification.
+# define _GLIBCXX_NOT_FN_CALL_OP( _QUALS ) \
+ template<typename... _Args, \
+ typename = __enable_if_t<__is_invocable<_Fn _QUALS, _Args...>::value>> \
+ _GLIBCXX20_CONSTEXPR \
+ decltype(_S_not<__inv_res_t<_Fn _QUALS, _Args...>>()) \
+ operator()(_Args&&... __args) _QUALS \
+ noexcept(__is_nothrow_invocable<_Fn _QUALS, _Args...>::value \
+ && noexcept(_S_not<__inv_res_t<_Fn _QUALS, _Args...>>())) \
+ { \
+ return !std::__invoke(std::forward< _Fn _QUALS >(_M_fn), \
+ std::forward<_Args>(__args)...); \
+ } \
+ \
+ template<typename... _Args, \
+ typename = __enable_if_t<!__is_invocable<_Fn _QUALS, _Args...>::value>> \
+ void operator()(_Args&&... __args) _QUALS = delete;
+
+ _GLIBCXX_NOT_FN_CALL_OP( & )
+ _GLIBCXX_NOT_FN_CALL_OP( const & )
+ _GLIBCXX_NOT_FN_CALL_OP( && )
+ _GLIBCXX_NOT_FN_CALL_OP( const && )
+# undef _GLIBCXX_NOT_FN_CALL_OP
+#else
+ /// Generalized negator.
+ template<typename _Fn, typename _Ite>
+ class _Not_fn
+ {
+ public:
+ _Not_fn(_Fn __fn)
+ : _M_fn(__fn) { }
+
+ bool
+ operator()(typename std::iterator_traits<_Ite>::reference __arg)
+ { return !bool(_M_fn(__arg)); }
+#endif
+ private:
+ _Fn _M_fn;
};
- template<typename _Predicate>
- _GLIBCXX20_CONSTEXPR
- inline _Iter_negate<_Predicate>
- __negate(_Iter_pred<_Predicate> __pred)
- { return _Iter_negate<_Predicate>(_GLIBCXX_MOVE(__pred._M_pred)); }
+ template<typename _Fn, typename _Ite>
+ inline _GLIBCXX20_CONSTEXPR
+#if __cplusplus >= 201103L
+ _Not_fn<std::__decay_t<_Fn>>
+ __not_fn(_Fn&& __fn, _Ite)
+ noexcept(std::is_nothrow_constructible<std::__decay_t<_Fn>, _Fn&&>::value)
+ { return _Not_fn<std::__decay_t<_Fn>>{std::forward<_Fn>(__fn), 0}; }
+#else
+ _Not_fn<_Fn, _Ite>
+ __not_fn(_Fn __fn, _Ite)
+ { return _Not_fn<_Fn, _Ite>(__fn); }
+#endif
-} // namespace __ops
-} // namespace __gnu_cxx
+_GLIBCXX_END_NAMESPACE_VERSION
+} // namespace std
#endif
diff --git a/libstdc++-v3/include/bits/stl_algo.h b/libstdc++-v3/include/bits/stl_algo.h
index a1ef665506d..5eb22ed98e1 100644
--- a/libstdc++-v3/include/bits/stl_algo.h
+++ b/libstdc++-v3/include/bits/stl_algo.h
@@ -85,21 +85,21 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
template<typename _Iterator, typename _Compare>
_GLIBCXX20_CONSTEXPR
void
- __move_median_to_first(_Iterator __result,_Iterator __a, _Iterator __b,
- _Iterator __c, _Compare __comp)
+ __move_median_to_first(_Iterator __result, _Iterator __a, _Iterator __b,
+ _Iterator __c, _GLIBCXX_FWDREF(_Compare) __comp)
{
- if (__comp(__a, __b))
+ if (__comp(*__a, *__b))
{
- if (__comp(__b, __c))
+ if (__comp(*__b, *__c))
std::iter_swap(__result, __b);
- else if (__comp(__a, __c))
+ else if (__comp(*__a, *__c))
std::iter_swap(__result, __c);
else
std::iter_swap(__result, __a);
}
- else if (__comp(__a, __c))
+ else if (__comp(*__a, *__c))
std::iter_swap(__result, __a);
- else if (__comp(__b, __c))
+ else if (__comp(*__b, *__c))
std::iter_swap(__result, __c);
else
std::iter_swap(__result, __b);
@@ -110,10 +110,11 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX20_CONSTEXPR
inline _InputIterator
__find_if_not(_InputIterator __first, _InputIterator __last,
- _Predicate __pred)
+ _GLIBCXX_FWDREF(_Predicate) __pred)
{
- return std::__find_if(__first, __last,
- __gnu_cxx::__ops::__negate(__pred));
+ __decltype(std::__not_fn(_GLIBCXX_FORWARD(_Predicate, __pred), __first))
+ __prd = std::__not_fn(_GLIBCXX_FORWARD(_Predicate, __pred), __first);
+ return std::__find_if(__first, __last, _GLIBCXX_MOVE(__prd));
}
/// Like find_if_not(), but uses and updates a count of the
@@ -122,10 +123,11 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
template<typename _InputIterator, typename _Predicate, typename _Distance>
_GLIBCXX20_CONSTEXPR
_InputIterator
- __find_if_not_n(_InputIterator __first, _Distance& __len, _Predicate __pred)
+ __find_if_not_n(_InputIterator __first, _Distance& __len,
+ _GLIBCXX_FWDREF(_Predicate) __pred)
{
for (; __len; --__len, (void) ++__first)
- if (!__pred(__first))
+ if (!__pred(*__first))
break;
return __first;
}
@@ -152,7 +154,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX20_CONSTEXPR
_ForwardIterator
__search_n_aux(_ForwardIterator __first, _ForwardIterator __last,
- _Integer __count, _UnaryPredicate __unary_pred,
+ _Integer __count,
+ _GLIBCXX_FWDREF(_UnaryPredicate) __unary_pred,
std::forward_iterator_tag)
{
__first = std::__find_if(__first, __last, __unary_pred);
@@ -162,7 +165,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__n = __count;
_ForwardIterator __i = __first;
++__i;
- while (__i != __last && __n != 1 && __unary_pred(__i))
+ while (__i != __last && __n != 1 && __unary_pred(*__i))
{
++__i;
--__n;
@@ -185,7 +188,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX20_CONSTEXPR
_RandomAccessIter
__search_n_aux(_RandomAccessIter __first, _RandomAccessIter __last,
- _Integer __count, _UnaryPredicate __unary_pred,
+ _Integer __count,
+ _GLIBCXX_FWDREF(_UnaryPredicate) __unary_pred,
std::random_access_iterator_tag)
{
typedef typename std::iterator_traits<_RandomAccessIter>::difference_type
@@ -201,7 +205,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
// __first here is always pointing to one past the last element of
// next possible match.
_RandomAccessIter __backTrack = __first;
- while (__unary_pred(--__backTrack))
+ while (__unary_pred(*(--__backTrack)))
{
if (--__remainder == 0)
return (__first - __count); // Success
@@ -217,16 +221,18 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_ForwardIterator
__search_n(_ForwardIterator __first, _ForwardIterator __last,
_Integer __count,
- _UnaryPredicate __unary_pred)
+ _GLIBCXX_FWDREF(_UnaryPredicate) __unary_pred)
{
if (__count <= 0)
return __first;
if (__count == 1)
- return std::__find_if(__first, __last, __unary_pred);
+ return std::__find_if
+ (__first, __last, _GLIBCXX_FORWARD(_UnaryPredicate, __unary_pred));
- return std::__search_n_aux(__first, __last, __count, __unary_pred,
- std::__iterator_category(__first));
+ return std::__search_n_aux(__first, __last, __count,
+ _GLIBCXX_FORWARD(_UnaryPredicate, __unary_pred),
+ std::__iterator_category(__first));
}
// find_end for forward iterators.
@@ -237,7 +243,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__find_end(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
_ForwardIterator2 __first2, _ForwardIterator2 __last2,
forward_iterator_tag, forward_iterator_tag,
- _BinaryPredicate __comp)
+ _GLIBCXX_FWDREF(_BinaryPredicate) __comp)
{
if (__first2 == __last2)
return __last1;
@@ -268,7 +274,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_BidirectionalIterator2 __first2,
_BidirectionalIterator2 __last2,
bidirectional_iterator_tag, bidirectional_iterator_tag,
- _BinaryPredicate __comp)
+ _GLIBCXX_FWDREF(_BinaryPredicate) __comp)
{
// concept requirements
__glibcxx_function_requires(_BidirectionalIteratorConcept<
@@ -283,7 +289,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_RevIterator2 __rlast2(__first2);
_RevIterator1 __rresult = std::__search(_RevIterator1(__last1), __rlast1,
_RevIterator2(__last2), __rlast2,
- __comp);
+ _GLIBCXX_FORWARD(_BinaryPredicate, __comp));
if (__rresult == __rlast1)
return __last1;
@@ -336,10 +342,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__glibcxx_requires_valid_range(__first1, __last1);
__glibcxx_requires_valid_range(__first2, __last2);
+ __decltype(__gnu_cxx::__ops::__equal_to(__first1, __first2)) __comp =
+ __gnu_cxx::__ops::__equal_to(__first1, __first2);
return std::__find_end(__first1, __last1, __first2, __last2,
std::__iterator_category(__first1),
std::__iterator_category(__first2),
- __gnu_cxx::__ops::__iter_equal_to_iter());
+ __comp);
}
/**
@@ -390,7 +398,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
return std::__find_end(__first1, __last1, __first2, __last2,
std::__iterator_category(__first1),
std::__iterator_category(__first2),
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ _GLIBCXX_MOVE(__comp));
}
#if __cplusplus >= 201103L
@@ -410,7 +418,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX_NODISCARD _GLIBCXX20_CONSTEXPR
inline bool
all_of(_InputIterator __first, _InputIterator __last, _Predicate __pred)
- { return __last == std::find_if_not(__first, __last, __pred); }
+ { return __last == std::find_if_not(__first, __last, std::move(__pred)); }
/**
* @brief Checks that a predicate is false for all the elements
@@ -428,7 +436,10 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX_NODISCARD _GLIBCXX20_CONSTEXPR
inline bool
none_of(_InputIterator __first, _InputIterator __last, _Predicate __pred)
- { return __last == _GLIBCXX_STD_A::find_if(__first, __last, __pred); }
+ {
+ return
+ __last == _GLIBCXX_STD_A::find_if(__first, __last, std::move(__pred));
+ }
/**
* @brief Checks that a predicate is true for at least one element
@@ -447,7 +458,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX_NODISCARD _GLIBCXX20_CONSTEXPR
inline bool
any_of(_InputIterator __first, _InputIterator __last, _Predicate __pred)
- { return !std::none_of(__first, __last, __pred); }
+ { return !std::none_of(__first, __last, std::move(__pred)); }
/**
* @brief Find the first element in a sequence for which a
@@ -470,8 +481,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__glibcxx_function_requires(_UnaryPredicateConcept<_Predicate,
typename iterator_traits<_InputIterator>::value_type>)
__glibcxx_requires_valid_range(__first, __last);
- return std::__find_if_not(__first, __last,
- __gnu_cxx::__ops::__pred_iter(__pred));
+ return std::__find_if_not(__first, __last, std::move(__pred));
}
/**
@@ -494,7 +504,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
if (__first == __last)
return true;
++__first;
- return std::none_of(__first, __last, __pred);
+ return std::none_of(__first, __last, std::move(__pred));
}
/**
@@ -541,17 +551,18 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
}
return __first;
}
-#endif
+#endif // C++11
template<typename _InputIterator, typename _OutputIterator,
typename _Predicate>
_GLIBCXX20_CONSTEXPR
_OutputIterator
__remove_copy_if(_InputIterator __first, _InputIterator __last,
- _OutputIterator __result, _Predicate __pred)
+ _OutputIterator __result,
+ _GLIBCXX_FWDREF(_Predicate) __pred)
{
for (; __first != __last; ++__first)
- if (!__pred(__first))
+ if (!__pred(*__first))
{
*__result = *__first;
++__result;
@@ -587,8 +598,9 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
typename iterator_traits<_InputIterator>::value_type, _Tp>)
__glibcxx_requires_valid_range(__first, __last);
- return std::__remove_copy_if(__first, __last, __result,
- __gnu_cxx::__ops::__iter_equals_val(__value));
+ __decltype(__gnu_cxx::__ops::__equal_val(__first, __value)) __pred =
+ __gnu_cxx::__ops::__equal_val(__first, __value);
+ return std::__remove_copy_if(__first, __last, __result, __pred);
}
/**
@@ -622,7 +634,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__glibcxx_requires_valid_range(__first, __last);
return std::__remove_copy_if(__first, __last, __result,
- __gnu_cxx::__ops::__pred_iter(__pred));
+ _GLIBCXX_MOVE(__pred));
}
#if __cplusplus >= 201103L
@@ -797,8 +809,9 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
typename iterator_traits<_ForwardIterator>::value_type, _Tp>)
__glibcxx_requires_valid_range(__first, __last);
- return std::__remove_if(__first, __last,
- __gnu_cxx::__ops::__iter_equals_val(__value));
+ __decltype(__gnu_cxx::__ops::__equal_val(__first, __value)) __comp =
+ __gnu_cxx::__ops::__equal_val(__first, __value);
+ return std::__remove_if(__first, __last, __comp);
}
/**
@@ -831,22 +844,21 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
typename iterator_traits<_ForwardIterator>::value_type>)
__glibcxx_requires_valid_range(__first, __last);
- return std::__remove_if(__first, __last,
- __gnu_cxx::__ops::__pred_iter(__pred));
+ return std::__remove_if(__first, __last, _GLIBCXX_MOVE(__pred));
}
template<typename _ForwardIterator, typename _BinaryPredicate>
_GLIBCXX20_CONSTEXPR
_ForwardIterator
__adjacent_find(_ForwardIterator __first, _ForwardIterator __last,
- _BinaryPredicate __binary_pred)
+ _GLIBCXX_FWDREF(_BinaryPredicate) __binary_pred)
{
if (__first == __last)
return __last;
_ForwardIterator __next = __first;
while (++__next != __last)
{
- if (__binary_pred(__first, __next))
+ if (__binary_pred(*__first, *__next))
return __first;
__first = __next;
}
@@ -857,7 +869,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX20_CONSTEXPR
_ForwardIterator
__unique(_ForwardIterator __first, _ForwardIterator __last,
- _BinaryPredicate __binary_pred)
+ _GLIBCXX_FWDREF(_BinaryPredicate) __binary_pred)
{
// Skip the beginning, if already unique.
__first = std::__adjacent_find(__first, __last, __binary_pred);
@@ -868,7 +880,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_ForwardIterator __dest = __first;
++__first;
while (++__first != __last)
- if (!__binary_pred(__dest, __first))
+ if (!__binary_pred(*__dest, *__first))
*++__dest = _GLIBCXX_MOVE(*__first);
return ++__dest;
}
@@ -899,8 +911,9 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
typename iterator_traits<_ForwardIterator>::value_type>)
__glibcxx_requires_valid_range(__first, __last);
- return std::__unique(__first, __last,
- __gnu_cxx::__ops::__iter_equal_to_iter());
+ __decltype(__gnu_cxx::__ops::__equal_to(__first)) __comp =
+ __gnu_cxx::__ops::__equal_to(__first);
+ return std::__unique(__first, __last, __comp);
}
/**
@@ -932,8 +945,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
typename iterator_traits<_ForwardIterator>::value_type>)
__glibcxx_requires_valid_range(__first, __last);
- return std::__unique(__first, __last,
- __gnu_cxx::__ops::__iter_comp_iter(__binary_pred));
+ return std::__unique(__first, __last, _GLIBCXX_MOVE(__binary_pred));
}
/**
@@ -947,7 +959,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX20_CONSTEXPR
_OutputIterator
__unique_copy(_ForwardIterator __first, _ForwardIterator __last,
- _OutputIterator __result, _BinaryPredicate __binary_pred,
+ _OutputIterator __result,
+ _GLIBCXX_FWDREF(_BinaryPredicate) __binary_pred,
forward_iterator_tag, output_iterator_tag)
{
// concept requirements -- iterators already checked
@@ -958,7 +971,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_ForwardIterator __next = __first;
*__result = *__first;
while (++__next != __last)
- if (!__binary_pred(__first, __next))
+ if (!__binary_pred(*__first, *__next))
{
__first = __next;
*++__result = *__first;
@@ -977,7 +990,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX20_CONSTEXPR
_OutputIterator
__unique_copy(_InputIterator __first, _InputIterator __last,
- _OutputIterator __result, _BinaryPredicate __binary_pred,
+ _OutputIterator __result,
+ _GLIBCXX_FWDREF(_BinaryPredicate) __binary_pred,
input_iterator_tag, output_iterator_tag)
{
// concept requirements -- iterators already checked
@@ -986,12 +1000,14 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
typename iterator_traits<_InputIterator>::value_type>)
typename iterator_traits<_InputIterator>::value_type __value = *__first;
- __decltype(__gnu_cxx::__ops::__iter_comp_val(__binary_pred))
- __rebound_pred
- = __gnu_cxx::__ops::__iter_comp_val(__binary_pred);
+ __decltype(__gnu_cxx::__ops::__equal_to_val
+ (_GLIBCXX_FORWARD(_BinaryPredicate, __binary_pred),
+ __first, __value)) __bnry_pred =
+ __gnu_cxx::__ops::__equal_to_val
+ (_GLIBCXX_FORWARD(_BinaryPredicate, __binary_pred), __first, __value);
*__result = __value;
while (++__first != __last)
- if (!__rebound_pred(__first, __value))
+ if (!__bnry_pred(*__first, __value))
{
__value = *__first;
*++__result = __value;
@@ -1010,7 +1026,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX20_CONSTEXPR
_ForwardIterator
__unique_copy(_InputIterator __first, _InputIterator __last,
- _ForwardIterator __result, _BinaryPredicate __binary_pred,
+ _ForwardIterator __result,
+ _GLIBCXX_FWDREF(_BinaryPredicate) __binary_pred,
input_iterator_tag, forward_iterator_tag)
{
// concept requirements -- iterators already checked
@@ -1019,7 +1036,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
typename iterator_traits<_InputIterator>::value_type>)
*__result = *__first;
while (++__first != __last)
- if (!__binary_pred(__result, __first))
+ if (!__binary_pred(*__result, *__first))
*++__result = *__first;
return ++__result;
}
@@ -1404,7 +1421,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_GLIBCXX20_CONSTEXPR
_ForwardIterator
__partition(_ForwardIterator __first, _ForwardIterator __last,
- _Predicate __pred, forward_iterator_tag)
+ _GLIBCXX_FWDREF(_Predicate) __pred, forward_iterator_tag)
{
if (__first == __last)
return __first;
@@ -1430,7 +1447,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_GLIBCXX20_CONSTEXPR
_BidirectionalIterator
__partition(_BidirectionalIterator __first, _BidirectionalIterator __last,
- _Predicate __pred, bidirectional_iterator_tag)
+ _GLIBCXX_FWDREF(_Predicate) __pred, bidirectional_iterator_tag)
{
while (true)
{
@@ -1468,7 +1485,8 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_ForwardIterator
__stable_partition_adaptive(_ForwardIterator __first,
_ForwardIterator __last,
- _Predicate __pred, _Distance __len,
+ _GLIBCXX_FWDREF(_Predicate) __pred,
+ _Distance __len,
_Pointer __buffer,
_Distance __buffer_size)
{
@@ -1487,7 +1505,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
++__result2;
++__first;
for (; __first != __last; ++__first)
- if (__pred(__first))
+ if (__pred(*__first))
{
*__result1 = _GLIBCXX_MOVE(*__first);
++__result1;
@@ -1517,7 +1535,8 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
if (__right_len)
__right_split =
- std::__stable_partition_adaptive(__right_split, __last, __pred,
+ std::__stable_partition_adaptive(__right_split, __last,
+ _GLIBCXX_FORWARD(_Predicate, __pred),
__right_len,
__buffer, __buffer_size);
@@ -1527,7 +1546,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
template<typename _ForwardIterator, typename _Predicate>
_ForwardIterator
__stable_partition(_ForwardIterator __first, _ForwardIterator __last,
- _Predicate __pred)
+ _GLIBCXX_FWDREF(_Predicate) __pred)
{
__first = std::__find_if_not(__first, __last, __pred);
@@ -1542,7 +1561,8 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_Temporary_buffer<_ForwardIterator, _ValueType>
__buf(__first, std::distance(__first, __last));
return
- std::__stable_partition_adaptive(__first, __last, __pred,
+ std::__stable_partition_adaptive(__first, __last,
+ _GLIBCXX_FORWARD(_Predicate, __pred),
_DistanceType(__buf.requested_size()),
__buf.begin(),
_DistanceType(__buf.size()));
@@ -1578,7 +1598,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_valid_range(__first, __last);
return std::__stable_partition(__first, __last,
- __gnu_cxx::__ops::__pred_iter(__pred));
+ _GLIBCXX_MOVE(__pred));
}
#endif // HOSTED
@@ -1590,11 +1610,12 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
void
__heap_select(_RandomAccessIterator __first,
_RandomAccessIterator __middle,
- _RandomAccessIterator __last, _Compare __comp)
+ _RandomAccessIterator __last,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
std::__make_heap(__first, __middle, __comp);
for (_RandomAccessIterator __i = __middle; __i < __last; ++__i)
- if (__comp(__i, __first))
+ if (__comp(*__i, *__first))
std::__pop_heap(__first, __middle, __i, __comp);
}
@@ -1607,7 +1628,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__partial_sort_copy(_InputIterator __first, _InputIterator __last,
_RandomAccessIterator __result_first,
_RandomAccessIterator __result_last,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
typedef typename iterator_traits<_InputIterator>::value_type
_InputValueType;
@@ -1627,14 +1648,15 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
std::__make_heap(__result_first, __result_real_last, __comp);
while (__first != __last)
{
- if (__comp(__first, __result_first))
+ if (__comp(*__first, *__result_first))
std::__adjust_heap(__result_first, _DistanceType(0),
_DistanceType(__result_real_last
- __result_first),
_InputValueType(*__first), __comp);
++__first;
}
- std::__sort_heap(__result_first, __result_real_last, __comp);
+ std::__sort_heap(__result_first, __result_real_last,
+ _GLIBCXX_FORWARD(_Compare, __comp));
return __result_real_last;
}
@@ -1683,9 +1705,11 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_irreflexive(__first, __last);
__glibcxx_requires_valid_range(__result_first, __result_last);
+ __decltype(__gnu_cxx::__ops::__less(__first, __result_first)) __comp =
+ __gnu_cxx::__ops::__less(__first, __result_first);
return std::__partial_sort_copy(__first, __last,
__result_first, __result_last,
- __gnu_cxx::__ops::__iter_less_iter());
+ __comp);
}
/**
@@ -1740,23 +1764,21 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
return std::__partial_sort_copy(__first, __last,
__result_first, __result_last,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ _GLIBCXX_MOVE(__comp));
}
/// @cond undocumented
/// This is a helper function for the sort routine.
- template<typename _RandomAccessIterator, typename _Compare>
+ template<typename _RandomAccessIterator, typename _Val, typename _Compare>
_GLIBCXX20_CONSTEXPR
void
- __unguarded_linear_insert(_RandomAccessIterator __last,
- _Compare __comp)
+ __unguarded_linear_insert(_RandomAccessIterator __last, _Val __val,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
- typename iterator_traits<_RandomAccessIterator>::value_type
- __val = _GLIBCXX_MOVE(*__last);
_RandomAccessIterator __next = __last;
--__next;
- while (__comp(__val, __next))
+ while (__comp(__val, *__next))
{
*__last = _GLIBCXX_MOVE(*__next);
__last = __next;
@@ -1770,13 +1792,14 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_GLIBCXX20_CONSTEXPR
void
__insertion_sort(_RandomAccessIterator __first,
- _RandomAccessIterator __last, _Compare __comp)
+ _RandomAccessIterator __last,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
if (__first == __last) return;
for (_RandomAccessIterator __i = __first + 1; __i != __last; ++__i)
{
- if (__comp(__i, __first))
+ if (__comp(*__i, *__first))
{
typename iterator_traits<_RandomAccessIterator>::value_type
__val = _GLIBCXX_MOVE(*__i);
@@ -1784,8 +1807,12 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
*__first = _GLIBCXX_MOVE(__val);
}
else
- std::__unguarded_linear_insert(__i,
- __gnu_cxx::__ops::__val_comp_iter(__comp));
+ {
+ typename iterator_traits<_RandomAccessIterator>::value_type
+ __val = _GLIBCXX_MOVE(*__i);
+ std::__unguarded_linear_insert(__i,
+ _GLIBCXX_MOVE(__val), __comp);
+ }
}
}
@@ -1794,11 +1821,16 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_GLIBCXX20_CONSTEXPR
inline void
__unguarded_insertion_sort(_RandomAccessIterator __first,
- _RandomAccessIterator __last, _Compare __comp)
+ _RandomAccessIterator __last,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
for (_RandomAccessIterator __i = __first; __i != __last; ++__i)
- std::__unguarded_linear_insert(__i,
- __gnu_cxx::__ops::__val_comp_iter(__comp));
+ {
+ typename std::iterator_traits<_RandomAccessIterator>::value_type
+ __val = _GLIBCXX_MOVE(*__i);
+ std::__unguarded_linear_insert(__i,
+ _GLIBCXX_MOVE(__val), __comp);
+ }
}
/**
@@ -1812,16 +1844,18 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_GLIBCXX20_CONSTEXPR
void
__final_insertion_sort(_RandomAccessIterator __first,
- _RandomAccessIterator __last, _Compare __comp)
+ _RandomAccessIterator __last,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
if (__last - __first > int(_S_threshold))
{
std::__insertion_sort(__first, __first + int(_S_threshold), __comp);
std::__unguarded_insertion_sort(__first + int(_S_threshold), __last,
- __comp);
+ _GLIBCXX_FORWARD(_Compare, __comp));
}
else
- std::__insertion_sort(__first, __last, __comp);
+ std::__insertion_sort(__first, __last,
+ _GLIBCXX_FORWARD(_Compare, __comp));
}
/// This is a helper function...
@@ -1830,14 +1864,15 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_RandomAccessIterator
__unguarded_partition(_RandomAccessIterator __first,
_RandomAccessIterator __last,
- _RandomAccessIterator __pivot, _Compare __comp)
+ _RandomAccessIterator __pivot,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
while (true)
{
- while (__comp(__first, __pivot))
+ while (__comp(*__first, *__pivot))
++__first;
--__last;
- while (__comp(__pivot, __last))
+ while (__comp(*__pivot, *__last))
--__last;
if (!(__first < __last))
return __first;
@@ -1851,12 +1886,14 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_GLIBCXX20_CONSTEXPR
inline _RandomAccessIterator
__unguarded_partition_pivot(_RandomAccessIterator __first,
- _RandomAccessIterator __last, _Compare __comp)
+ _RandomAccessIterator __last,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
_RandomAccessIterator __mid = __first + (__last - __first) / 2;
std::__move_median_to_first(__first, __first + 1, __mid, __last - 1,
__comp);
- return std::__unguarded_partition(__first + 1, __last, __first, __comp);
+ return std::__unguarded_partition(__first + 1, __last, __first,
+ _GLIBCXX_FORWARD(_Compare, __comp));
}
template<typename _RandomAccessIterator, typename _Compare>
@@ -1865,10 +1902,10 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__partial_sort(_RandomAccessIterator __first,
_RandomAccessIterator __middle,
_RandomAccessIterator __last,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
std::__heap_select(__first, __middle, __last, __comp);
- std::__sort_heap(__first, __middle, __comp);
+ std::__sort_heap(__first, __middle, _GLIBCXX_FORWARD(_Compare, __comp));
}
/// This is a helper function for the sort routine.
@@ -1877,13 +1914,14 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
void
__introsort_loop(_RandomAccessIterator __first,
_RandomAccessIterator __last,
- _Size __depth_limit, _Compare __comp)
+ _Size __depth_limit, _GLIBCXX_FWDREF(_Compare) __comp)
{
while (__last - __first > int(_S_threshold))
{
if (__depth_limit == 0)
{
- std::__partial_sort(__first, __last, __last, __comp);
+ std::__partial_sort(__first, __last, __last,
+ _GLIBCXX_FORWARD(_Compare, __comp));
return;
}
--__depth_limit;
@@ -1900,14 +1938,15 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_GLIBCXX20_CONSTEXPR
inline void
__sort(_RandomAccessIterator __first, _RandomAccessIterator __last,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
if (__first != __last)
{
std::__introsort_loop(__first, __last,
std::__lg(__last - __first) * 2,
__comp);
- std::__final_insertion_sort(__first, __last, __comp);
+ std::__final_insertion_sort(__first, __last,
+ _GLIBCXX_FORWARD(_Compare, __comp));
}
}
@@ -1916,13 +1955,14 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
void
__introselect(_RandomAccessIterator __first, _RandomAccessIterator __nth,
_RandomAccessIterator __last, _Size __depth_limit,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
while (__last - __first > 3)
{
if (__depth_limit == 0)
{
- std::__heap_select(__first, __nth + 1, __last, __comp);
+ std::__heap_select(__first, __nth + 1, __last,
+ _GLIBCXX_FORWARD(_Compare, __comp));
// Place the nth largest element in its final position.
std::iter_swap(__first, __nth);
return;
@@ -1935,7 +1975,8 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
else
__last = __cut;
}
- std::__insertion_sort(__first, __last, __comp);
+ std::__insertion_sort(__first, __last,
+ _GLIBCXX_FORWARD(_Compare, __comp));
}
/// @endcond
@@ -1973,14 +2014,14 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__val, __comp);
return std::__lower_bound(__first, __last, __val,
- __gnu_cxx::__ops::__iter_comp_val(__comp));
+ _GLIBCXX_MOVE(__comp));
}
template<typename _ForwardIterator, typename _Tp, typename _Compare>
_GLIBCXX20_CONSTEXPR
_ForwardIterator
__upper_bound(_ForwardIterator __first, _ForwardIterator __last,
- const _Tp& __val, _Compare __comp)
+ const _Tp& __val, _GLIBCXX_FWDREF(_Compare) __comp)
{
typedef typename iterator_traits<_ForwardIterator>::difference_type
_DistanceType;
@@ -1992,7 +2033,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_DistanceType __half = __len >> 1;
_ForwardIterator __middle = __first;
std::advance(__middle, __half);
- if (__comp(__val, __middle))
+ if (__comp(__val, *__middle))
__len = __half;
else
{
@@ -2027,8 +2068,9 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_Tp, typename iterator_traits<_ForwardIterator>::value_type>)
__glibcxx_requires_partitioned_upper(__first, __last, __val);
- return std::__upper_bound(__first, __last, __val,
- __gnu_cxx::__ops::__val_less_iter());
+ __decltype(__gnu_cxx::__ops::__less_val(__first, __val)) __comp =
+ __gnu_cxx::__ops::__less_val(__first, __val);
+ return std::__upper_bound(__first, __last, __val, __comp);
}
/**
@@ -2059,17 +2101,14 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_partitioned_upper_pred(__first, __last,
__val, __comp);
- return std::__upper_bound(__first, __last, __val,
- __gnu_cxx::__ops::__val_comp_iter(__comp));
+ return std::__upper_bound(__first, __last, __val, _GLIBCXX_MOVE(__comp));
}
- template<typename _ForwardIterator, typename _Tp,
- typename _CompareItTp, typename _CompareTpIt>
+ template<typename _ForwardIterator, typename _Tp, typename _Comp>
_GLIBCXX20_CONSTEXPR
pair<_ForwardIterator, _ForwardIterator>
__equal_range(_ForwardIterator __first, _ForwardIterator __last,
- const _Tp& __val,
- _CompareItTp __comp_it_val, _CompareTpIt __comp_val_it)
+ const _Tp& __val, _GLIBCXX_FWDREF(_Comp) __comp)
{
typedef typename iterator_traits<_ForwardIterator>::difference_type
_DistanceType;
@@ -2081,21 +2120,22 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_DistanceType __half = __len >> 1;
_ForwardIterator __middle = __first;
std::advance(__middle, __half);
- if (__comp_it_val(__middle, __val))
+ if (__comp(*__middle, __val))
{
__first = __middle;
++__first;
__len = __len - __half - 1;
}
- else if (__comp_val_it(__val, __middle))
+ else if (__comp(__val, *__middle))
__len = __half;
else
{
_ForwardIterator __left
- = std::__lower_bound(__first, __middle, __val, __comp_it_val);
+ = std::__lower_bound(__first, __middle, __val, __comp);
std::advance(__first, __len);
_ForwardIterator __right
- = std::__upper_bound(++__middle, __first, __val, __comp_val_it);
+ = std::__upper_bound(++__middle, __first, __val,
+ _GLIBCXX_FORWARD(_Comp, __comp));
return pair<_ForwardIterator, _ForwardIterator>(__left, __right);
}
}
@@ -2134,9 +2174,9 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_partitioned_lower(__first, __last, __val);
__glibcxx_requires_partitioned_upper(__first, __last, __val);
- return std::__equal_range(__first, __last, __val,
- __gnu_cxx::__ops::__iter_less_val(),
- __gnu_cxx::__ops::__val_less_iter());
+ __decltype(__gnu_cxx::__ops::__less_val(__first, __val)) __comp =
+ __gnu_cxx::__ops::__less_val(__first, __val);
+ return std::__equal_range(__first, __last, __val, __comp);
}
/**
@@ -2173,9 +2213,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_partitioned_upper_pred(__first, __last,
__val, __comp);
- return std::__equal_range(__first, __last, __val,
- __gnu_cxx::__ops::__iter_comp_val(__comp),
- __gnu_cxx::__ops::__val_comp_iter(__comp));
+ return std::__equal_range(__first, __last, __val, _GLIBCXX_MOVE(__comp));
}
/**
@@ -2203,9 +2241,10 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_partitioned_lower(__first, __last, __val);
__glibcxx_requires_partitioned_upper(__first, __last, __val);
- _ForwardIterator __i
- = std::__lower_bound(__first, __last, __val,
- __gnu_cxx::__ops::__iter_less_val());
+ __decltype(__gnu_cxx::__ops::__less_val(__first, __val)) __comp =
+ __gnu_cxx::__ops::__less_val(__first, __val);
+ _ForwardIterator __i =
+ std::__lower_bound(__first, __last, __val, __comp);
return __i != __last && !(__val < *__i);
}
@@ -2240,8 +2279,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__val, __comp);
_ForwardIterator __i
- = std::__lower_bound(__first, __last, __val,
- __gnu_cxx::__ops::__iter_comp_val(__comp));
+ = std::__lower_bound(__first, __last, __val, __comp);
return __i != __last && !bool(__comp(__val, *__i));
}
@@ -2253,11 +2291,12 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
void
__move_merge_adaptive(_InputIterator1 __first1, _InputIterator1 __last1,
_InputIterator2 __first2, _InputIterator2 __last2,
- _OutputIterator __result, _Compare __comp)
+ _OutputIterator __result,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
while (__first1 != __last1 && __first2 != __last2)
{
- if (__comp(__first2, __first1))
+ if (__comp(*__first2, *__first1))
{
*__result = _GLIBCXX_MOVE(*__first2);
++__first2;
@@ -2282,7 +2321,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_BidirectionalIterator2 __first2,
_BidirectionalIterator2 __last2,
_BidirectionalIterator3 __result,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
if (__first1 == __last1)
{
@@ -2296,7 +2335,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
--__last2;
while (true)
{
- if (__comp(__last2, __last1))
+ if (__comp(*__last2, *__last1))
{
*--__result = _GLIBCXX_MOVE(*__last1);
if (__first1 == __last1)
@@ -2362,19 +2401,23 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_BidirectionalIterator __middle,
_BidirectionalIterator __last,
_Distance __len1, _Distance __len2,
- _Pointer __buffer, _Compare __comp)
+ _Pointer __buffer, _GLIBCXX_FWDREF(_Compare) __comp)
{
+ __decltype(__gnu_cxx::__ops::__less(_GLIBCXX_FORWARD(_Compare, __comp),
+ __first, __buffer)) __cmp
+ = __gnu_cxx::__ops::__less(_GLIBCXX_FORWARD(_Compare, __comp),
+ __first, __buffer);
if (__len1 <= __len2)
{
_Pointer __buffer_end = _GLIBCXX_MOVE3(__first, __middle, __buffer);
std::__move_merge_adaptive(__buffer, __buffer_end, __middle, __last,
- __first, __comp);
+ __first, _GLIBCXX_FORWARD(_Compare, __cmp));
}
else
{
_Pointer __buffer_end = _GLIBCXX_MOVE3(__middle, __last, __buffer);
std::__move_merge_adaptive_backward(__first, __middle, __buffer,
- __buffer_end, __last, __comp);
+ __buffer_end, __last, _GLIBCXX_FORWARD(_Compare, __cmp));
}
}
@@ -2386,13 +2429,15 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_BidirectionalIterator __last,
_Distance __len1, _Distance __len2,
_Pointer __buffer, _Distance __buffer_size,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
if (__len1 <= __buffer_size || __len2 <= __buffer_size)
std::__merge_adaptive(__first, __middle, __last,
- __len1, __len2, __buffer, __comp);
+ __len1, __len2, __buffer, _GLIBCXX_FORWARD(_Compare, __comp));
else
{
+ typedef typename
+ std::iterator_traits<_BidirectionalIterator>::value_type _Val;
_BidirectionalIterator __first_cut = __first;
_BidirectionalIterator __second_cut = __middle;
_Distance __len11 = 0;
@@ -2401,18 +2446,18 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
{
__len11 = __len1 / 2;
std::advance(__first_cut, __len11);
+ const _Val& __val = *__first_cut;
__second_cut
- = std::__lower_bound(__middle, __last, *__first_cut,
- __gnu_cxx::__ops::__iter_comp_val(__comp));
+ = std::__lower_bound(__middle, __last, __val, __comp);
__len22 = std::distance(__middle, __second_cut);
}
else
{
__len22 = __len2 / 2;
std::advance(__second_cut, __len22);
+ const _Val& __val = *__second_cut;
__first_cut
- = std::__upper_bound(__first, __middle, *__second_cut,
- __gnu_cxx::__ops::__val_comp_iter(__comp));
+ = std::__upper_bound(__first, __middle, __val, __comp);
__len11 = std::distance(__first, __first_cut);
}
@@ -2426,7 +2471,8 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
std::__merge_adaptive_resize(__new_middle, __second_cut, __last,
_Distance(__len1 - __len11),
_Distance(__len2 - __len22),
- __buffer, __buffer_size, __comp);
+ __buffer, __buffer_size,
+ _GLIBCXX_FORWARD(_Compare, __comp));
}
}
@@ -2438,18 +2484,20 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_BidirectionalIterator __middle,
_BidirectionalIterator __last,
_Distance __len1, _Distance __len2,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
if (__len1 == 0 || __len2 == 0)
return;
if (__len1 + __len2 == 2)
{
- if (__comp(__middle, __first))
+ if (__comp(*__middle, *__first))
std::iter_swap(__first, __middle);
return;
}
+ typedef
+ typename std::iterator_traits<_BidirectionalIterator>::value_type _Val;
_BidirectionalIterator __first_cut = __first;
_BidirectionalIterator __second_cut = __middle;
_Distance __len11 = 0;
@@ -2458,18 +2506,18 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
{
__len11 = __len1 / 2;
std::advance(__first_cut, __len11);
+ const _Val& __val = *__first_cut;
__second_cut
- = std::__lower_bound(__middle, __last, *__first_cut,
- __gnu_cxx::__ops::__iter_comp_val(__comp));
+ = std::__lower_bound(__middle, __last, __val, __comp);
__len22 = std::distance(__middle, __second_cut);
}
else
{
__len22 = __len2 / 2;
std::advance(__second_cut, __len22);
+ const _Val& __val = *__second_cut;
__first_cut
- = std::__upper_bound(__first, __middle, *__second_cut,
- __gnu_cxx::__ops::__val_comp_iter(__comp));
+ = std::__upper_bound(__first, __middle, __val, __comp);
__len11 = std::distance(__first, __first_cut);
}
@@ -2478,7 +2526,8 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
std::__merge_without_buffer(__first, __first_cut, __new_middle,
__len11, __len22, __comp);
std::__merge_without_buffer(__new_middle, __second_cut, __last,
- __len1 - __len11, __len2 - __len22, __comp);
+ __len1 - __len11, __len2 - __len22,
+ _GLIBCXX_FORWARD(_Compare, __comp));
}
template<typename _BidirectionalIterator, typename _Compare>
@@ -2486,7 +2535,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__inplace_merge(_BidirectionalIterator __first,
_BidirectionalIterator __middle,
_BidirectionalIterator __last,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
typedef typename iterator_traits<_BidirectionalIterator>::value_type
_ValueType;
@@ -2507,17 +2556,21 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
if (__builtin_expect(__buf.size() == __buf.requested_size(), true))
std::__merge_adaptive
- (__first, __middle, __last, __len1, __len2, __buf.begin(), __comp);
+ (__first, __middle, __last, __len1, __len2, __buf.begin(),
+ _GLIBCXX_FORWARD(_Compare, __comp));
else if (__builtin_expect(__buf.begin() == 0, false))
std::__merge_without_buffer
- (__first, __middle, __last, __len1, __len2, __comp);
+ (__first, __middle, __last, __len1, __len2,
+ _GLIBCXX_FORWARD(_Compare, __comp));
else
std::__merge_adaptive_resize
(__first, __middle, __last, __len1, __len2, __buf.begin(),
- _DistanceType(__buf.size()), __comp);
+ _DistanceType(__buf.size()),
+ _GLIBCXX_FORWARD(_Compare, __comp));
#else
std::__merge_without_buffer
- (__first, __middle, __last, __len1, __len2, __comp);
+ (__first, __middle, __last, __len1, __len2,
+ _GLIBCXX_FORWARD(_Compare, __comp));
#endif
}
@@ -2554,8 +2607,9 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_sorted(__middle, __last);
__glibcxx_requires_irreflexive(__first, __last);
- std::__inplace_merge(__first, __middle, __last,
- __gnu_cxx::__ops::__iter_less_iter());
+ __decltype(__gnu_cxx::__ops::__less(__first)) __comp =
+ __gnu_cxx::__ops::__less(__first);
+ std::__inplace_merge(__first, __middle, __last, __comp);
}
/**
@@ -2597,8 +2651,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_sorted_pred(__middle, __last, __comp);
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
- std::__inplace_merge(__first, __middle, __last,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ std::__inplace_merge(__first, __middle, __last, _GLIBCXX_MOVE(__comp));
}
@@ -2608,11 +2661,11 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_OutputIterator
__move_merge(_InputIterator __first1, _InputIterator __last1,
_InputIterator __first2, _InputIterator __last2,
- _OutputIterator __result, _Compare __comp)
+ _OutputIterator __result, _GLIBCXX_FWDREF(_Compare) __comp)
{
while (__first1 != __last1 && __first2 != __last2)
{
- if (__comp(__first2, __first1))
+ if (__comp(*__first2, *__first1))
{
*__result = _GLIBCXX_MOVE(*__first2);
++__first2;
@@ -2635,7 +2688,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__merge_sort_loop(_RandomAccessIterator1 __first,
_RandomAccessIterator1 __last,
_RandomAccessIterator2 __result, _Distance __step_size,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
const _Distance __two_step = 2 * __step_size;
@@ -2650,7 +2703,8 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__step_size = std::min(_Distance(__last - __first), __step_size);
std::__move_merge(__first, __first + __step_size,
- __first + __step_size, __last, __result, __comp);
+ __first + __step_size, __last, __result,
+ _GLIBCXX_FORWARD(_Compare, __comp));
}
template<typename _RandomAccessIterator, typename _Distance,
@@ -2659,14 +2713,16 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
void
__chunk_insertion_sort(_RandomAccessIterator __first,
_RandomAccessIterator __last,
- _Distance __chunk_size, _Compare __comp)
+ _Distance __chunk_size,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
while (__last - __first >= __chunk_size)
{
std::__insertion_sort(__first, __first + __chunk_size, __comp);
__first += __chunk_size;
}
- std::__insertion_sort(__first, __last, __comp);
+ std::__insertion_sort
+ (__first, __last, _GLIBCXX_FORWARD(_Compare, __comp));
}
enum { _S_chunk_size = 7 };
@@ -2675,7 +2731,8 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
void
__merge_sort_with_buffer(_RandomAccessIterator __first,
_RandomAccessIterator __last,
- _Pointer __buffer, _Compare __comp)
+ _Pointer __buffer,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
typedef typename iterator_traits<_RandomAccessIterator>::difference_type
_Distance;
@@ -2702,14 +2759,16 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__stable_sort_adaptive(_RandomAccessIterator __first,
_RandomAccessIterator __middle,
_RandomAccessIterator __last,
- _Pointer __buffer, _Compare __comp)
+ _Pointer __buffer, _GLIBCXX_FWDREF(_Compare) __comp)
{
- std::__merge_sort_with_buffer(__first, __middle, __buffer, __comp);
- std::__merge_sort_with_buffer(__middle, __last, __buffer, __comp);
+ __decltype(__gnu_cxx::__ops::__less(__comp, __first, __buffer)) __cmp
+ = __gnu_cxx::__ops::__less(__comp, __first, __buffer);
+ std::__merge_sort_with_buffer(__first, __middle, __buffer, __cmp);
+ std::__merge_sort_with_buffer(__middle, __last, __buffer, __cmp);
std::__merge_adaptive(__first, __middle, __last,
__middle - __first, __last - __middle,
- __buffer, __comp);
+ __buffer, _GLIBCXX_FORWARD(_Compare, __comp));
}
template<typename _RandomAccessIterator, typename _Pointer,
@@ -2718,7 +2777,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__stable_sort_adaptive_resize(_RandomAccessIterator __first,
_RandomAccessIterator __last,
_Pointer __buffer, _Distance __buffer_size,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
const _Distance __len = (__last - __first + 1) / 2;
const _RandomAccessIterator __middle = __first + __len;
@@ -2732,22 +2791,24 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_Distance(__middle - __first),
_Distance(__last - __middle),
__buffer, __buffer_size,
- __comp);
+ _GLIBCXX_FORWARD(_Compare, __comp));
}
else
std::__stable_sort_adaptive(__first, __middle, __last,
- __buffer, __comp);
+ __buffer, _GLIBCXX_FORWARD(_Compare, __comp));
}
/// This is a helper function for the stable sorting routines.
template<typename _RandomAccessIterator, typename _Compare>
void
__inplace_stable_sort(_RandomAccessIterator __first,
- _RandomAccessIterator __last, _Compare __comp)
+ _RandomAccessIterator __last,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
if (__last - __first < 15)
{
- std::__insertion_sort(__first, __last, __comp);
+ std::__insertion_sort
+ (__first, __last, _GLIBCXX_FORWARD(_Compare, __comp));
return;
}
_RandomAccessIterator __middle = __first + (__last - __first) / 2;
@@ -2756,7 +2817,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
std::__merge_without_buffer(__first, __middle, __last,
__middle - __first,
__last - __middle,
- __comp);
+ _GLIBCXX_FORWARD(_Compare, __comp));
}
// stable_sort
@@ -2772,13 +2833,13 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
bool
__includes(_InputIterator1 __first1, _InputIterator1 __last1,
_InputIterator2 __first2, _InputIterator2 __last2,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
while (__first1 != __last1 && __first2 != __last2)
{
- if (__comp(__first2, __first1))
+ if (__comp(*__first2, *__first1))
return false;
- if (!__comp(__first1, __first2))
+ if (!__comp(*__first1, *__first2))
++__first2;
++__first1;
}
@@ -2824,8 +2885,9 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_irreflexive2(__first1, __last1);
__glibcxx_requires_irreflexive2(__first2, __last2);
- return std::__includes(__first1, __last1, __first2, __last2,
- __gnu_cxx::__ops::__iter_less_iter());
+ __decltype(__gnu_cxx::__ops::__less(__first1, __first2)) __comp =
+ __gnu_cxx::__ops::__less(__first1, __first2);
+ return std::__includes(__first1, __last1, __first2, __last2, __comp);
}
/**
@@ -2872,7 +2934,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_irreflexive_pred2(__first2, __last2, __comp);
return std::__includes(__first1, __last1, __first2, __last2,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ _GLIBCXX_MOVE(__comp));
}
// nth_element
@@ -2889,7 +2951,8 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_GLIBCXX20_CONSTEXPR
bool
__next_permutation(_BidirectionalIterator __first,
- _BidirectionalIterator __last, _Compare __comp)
+ _BidirectionalIterator __last,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
if (__first == __last)
return false;
@@ -2904,10 +2967,10 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
{
_BidirectionalIterator __ii = __i;
--__i;
- if (__comp(__i, __ii))
+ if (__comp(*__i, *__ii))
{
_BidirectionalIterator __j = __last;
- while (!__comp(__i, --__j))
+ while (!__comp(*__i, *(--__j)))
{}
std::iter_swap(__i, __j);
std::__reverse(__ii, __last,
@@ -2949,8 +3012,9 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive(__first, __last);
- return std::__next_permutation
- (__first, __last, __gnu_cxx::__ops::__iter_less_iter());
+ __decltype(__gnu_cxx::__ops::__less(__first)) __comp =
+ __gnu_cxx::__ops::__less(__first);
+ return std::__next_permutation(__first, __last, __comp);
}
/**
@@ -2983,15 +3047,15 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
- return std::__next_permutation
- (__first, __last, __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ return std::__next_permutation(__first, __last, _GLIBCXX_MOVE(__comp));
}
template<typename _BidirectionalIterator, typename _Compare>
_GLIBCXX20_CONSTEXPR
bool
__prev_permutation(_BidirectionalIterator __first,
- _BidirectionalIterator __last, _Compare __comp)
+ _BidirectionalIterator __last,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
if (__first == __last)
return false;
@@ -3006,10 +3070,10 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
{
_BidirectionalIterator __ii = __i;
--__i;
- if (__comp(__ii, __i))
+ if (__comp(*__ii, *__i))
{
_BidirectionalIterator __j = __last;
- while (!__comp(--__j, __i))
+ while (!__comp(*(--__j), *__i))
{}
std::iter_swap(__i, __j);
std::__reverse(__ii, __last,
@@ -3052,8 +3116,9 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive(__first, __last);
- return std::__prev_permutation(__first, __last,
- __gnu_cxx::__ops::__iter_less_iter());
+ __decltype(__gnu_cxx::__ops::__less(__first)) __comp =
+ __gnu_cxx::__ops::__less(__first);
+ return std::__prev_permutation(__first, __last, __comp);
}
/**
@@ -3086,8 +3151,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
- return std::__prev_permutation(__first, __last,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ return std::__prev_permutation(__first, __last, _GLIBCXX_MOVE(__comp));
}
// replace
@@ -3099,10 +3163,11 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_OutputIterator
__replace_copy_if(_InputIterator __first, _InputIterator __last,
_OutputIterator __result,
- _Predicate __pred, const _Tp& __new_value)
+ _GLIBCXX_FWDREF(_Predicate) __pred,
+ const _Tp& __new_value)
{
for (; __first != __last; ++__first, (void)++__result)
- if (__pred(__first))
+ if (__pred(*__first))
*__result = __new_value;
else
*__result = *__first;
@@ -3138,9 +3203,10 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
typename iterator_traits<_InputIterator>::value_type, _Tp>)
__glibcxx_requires_valid_range(__first, __last);
+ __decltype(__gnu_cxx::__ops::__equal_val(__first, __old_value)) __pred =
+ __gnu_cxx::__ops::__equal_val(__first, __old_value);
return std::__replace_copy_if(__first, __last, __result,
- __gnu_cxx::__ops::__iter_equals_val(__old_value),
- __new_value);
+ __pred, __new_value);
}
/**
@@ -3175,8 +3241,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_valid_range(__first, __last);
return std::__replace_copy_if(__first, __last, __result,
- __gnu_cxx::__ops::__pred_iter(__pred),
- __new_value);
+ _GLIBCXX_MOVE(__pred), __new_value);
}
#if __cplusplus >= 201103L
@@ -3207,20 +3272,22 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
inline bool
is_sorted(_ForwardIterator __first, _ForwardIterator __last,
_Compare __comp)
- { return std::is_sorted_until(__first, __last, __comp) == __last; }
+ {
+ return std::is_sorted_until(__first, __last, std::move(__comp)) == __last;
+ }
template<typename _ForwardIterator, typename _Compare>
_GLIBCXX20_CONSTEXPR
_ForwardIterator
__is_sorted_until(_ForwardIterator __first, _ForwardIterator __last,
- _Compare __comp)
+ _Compare&& __comp)
{
if (__first == __last)
return __last;
_ForwardIterator __next = __first;
for (++__next; __next != __last; __first = __next, (void)++__next)
- if (__comp(__next, __first))
+ if (__comp(*__next, *__first))
return __next;
return __next;
}
@@ -3246,7 +3313,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_irreflexive(__first, __last);
return std::__is_sorted_until(__first, __last,
- __gnu_cxx::__ops::__iter_less_iter());
+ __gnu_cxx::__ops::__less());
}
/**
@@ -3272,8 +3339,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
- return std::__is_sorted_until(__first, __last,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ return std::__is_sorted_until(__first, __last, std::move(__comp));
}
/**
@@ -3318,7 +3384,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
_GLIBCXX14_CONSTEXPR
pair<_ForwardIterator, _ForwardIterator>
__minmax_element(_ForwardIterator __first, _ForwardIterator __last,
- _Compare __comp)
+ _Compare&& __comp)
{
_ForwardIterator __next = __first;
if (__first == __last
@@ -3326,7 +3392,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
return std::make_pair(__first, __first);
_ForwardIterator __min{}, __max{};
- if (__comp(__next, __first))
+ if (__comp(*__next, *__first))
{
__min = __next;
__max = __first;
@@ -3345,25 +3411,25 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__next = __first;
if (++__next == __last)
{
- if (__comp(__first, __min))
+ if (__comp(*__first, *__min))
__min = __first;
- else if (!__comp(__first, __max))
+ else if (!__comp(*__first, *__max))
__max = __first;
break;
}
- if (__comp(__next, __first))
+ if (__comp(*__next, *__first))
{
- if (__comp(__next, __min))
+ if (__comp(*__next, *__min))
__min = __next;
- if (!__comp(__first, __max))
+ if (!__comp(*__first, *__max))
__max = __first;
}
else
{
- if (__comp(__first, __min))
+ if (__comp(*__first, *__min))
__min = __first;
- if (!__comp(__next, __max))
+ if (!__comp(*__next, *__max))
__max = __next;
}
@@ -3398,7 +3464,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_irreflexive(__first, __last);
return std::__minmax_element(__first, __last,
- __gnu_cxx::__ops::__iter_less_iter());
+ __gnu_cxx::__ops::__less());
}
/**
@@ -3427,8 +3493,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
- return std::__minmax_element(__first, __last,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ return std::__minmax_element(__first, __last, std::move(__comp));
}
template<typename _Tp>
@@ -3439,7 +3504,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_irreflexive(__l.begin(), __l.end());
pair<const _Tp*, const _Tp*> __p =
std::__minmax_element(__l.begin(), __l.end(),
- __gnu_cxx::__ops::__iter_less_iter());
+ __gnu_cxx::__ops::__less());
return std::make_pair(*__p.first, *__p.second);
}
@@ -3450,8 +3515,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
{
__glibcxx_requires_irreflexive_pred(__l.begin(), __l.end(), __comp);
pair<const _Tp*, const _Tp*> __p =
- std::__minmax_element(__l.begin(), __l.end(),
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ std::__minmax_element(__l.begin(), __l.end(), std::move(__comp));
return std::make_pair(*__p.first, *__p.second);
}
@@ -3485,7 +3549,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_valid_range(__first1, __last1);
return std::__is_permutation(__first1, __last1, __first2,
- __gnu_cxx::__ops::__iter_comp_iter(__pred));
+ std::move(__pred));
}
#if __cplusplus > 201103L
@@ -3495,7 +3559,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
bool
__is_permutation(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
_ForwardIterator2 __first2, _ForwardIterator2 __last2,
- _BinaryPredicate __pred)
+ _BinaryPredicate&& __pred)
{
using _Cat1
= typename iterator_traits<_ForwardIterator1>::iterator_category;
@@ -3516,7 +3580,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
// have the same elements in the same order.
for (; __first1 != __last1 && __first2 != __last2;
++__first1, (void)++__first2)
- if (!__pred(__first1, __first2))
+ if (!__pred(*__first1, *__first2))
break;
if (__ra_iters)
@@ -3537,14 +3601,14 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
for (_ForwardIterator1 __scan = __first1; __scan != __last1; ++__scan)
{
if (__scan != std::__find_if(__first1, __scan,
- __gnu_cxx::__ops::__iter_comp_iter(__pred, __scan)))
+ __gnu_cxx::__ops::__equal_ite(__pred, __first1, __scan)))
continue; // We've seen this one before.
auto __matches = std::__count_if(__first2, __last2,
- __gnu_cxx::__ops::__iter_comp_iter(__pred, __scan));
+ __gnu_cxx::__ops::__equal_ite(__pred, __first2, __scan));
if (0 == __matches
|| std::__count_if(__scan, __last1,
- __gnu_cxx::__ops::__iter_comp_iter(__pred, __scan))
+ __gnu_cxx::__ops::__equal_ite(__pred, __first1, __scan))
!= __matches)
return false;
}
@@ -3575,7 +3639,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
return
std::__is_permutation(__first1, __last1, __first2, __last2,
- __gnu_cxx::__ops::__iter_equal_to_iter());
+ __gnu_cxx::__ops::__equal_to());
}
/**
@@ -3604,7 +3668,7 @@ _GLIBCXX_END_INLINE_ABI_NAMESPACE(_V2)
__glibcxx_requires_valid_range(__first2, __last2);
return std::__is_permutation(__first1, __last1, __first2, __last2,
- __gnu_cxx::__ops::__iter_comp_iter(__pred));
+ std::move(__pred));
}
#endif // C++14
@@ -3875,8 +3939,9 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
}
#endif
- return std::__find_if(__first, __last,
- __gnu_cxx::__ops::__iter_equals_val(__val));
+ __decltype(__gnu_cxx::__ops::__equal_val(__first, __val)) __comp =
+ __gnu_cxx::__ops::__equal_val(__first, __val);
+ return std::__find_if(__first, __last, __comp);
}
/**
@@ -3901,8 +3966,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
typename iterator_traits<_InputIterator>::value_type>)
__glibcxx_requires_valid_range(__first, __last);
- return std::__find_if(__first, __last,
- __gnu_cxx::__ops::__pred_iter(__pred));
+ return std::__find_if(__first, __last, _GLIBCXX_MOVE(__pred));
}
/**
@@ -4006,8 +4070,9 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
typename iterator_traits<_ForwardIterator>::value_type>)
__glibcxx_requires_valid_range(__first, __last);
- return std::__adjacent_find(__first, __last,
- __gnu_cxx::__ops::__iter_equal_to_iter());
+ __decltype(__gnu_cxx::__ops::__equal_to(__first)) __comp =
+ __gnu_cxx::__ops::__equal_to(__first);
+ return std::__adjacent_find(__first, __last, __comp);
}
/**
@@ -4035,7 +4100,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first, __last);
return std::__adjacent_find(__first, __last,
- __gnu_cxx::__ops::__iter_comp_iter(__binary_pred));
+ _GLIBCXX_MOVE(__binary_pred));
}
/**
@@ -4058,8 +4123,9 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
typename iterator_traits<_InputIterator>::value_type, _Tp>)
__glibcxx_requires_valid_range(__first, __last);
- return std::__count_if(__first, __last,
- __gnu_cxx::__ops::__iter_equals_val(__value));
+ __decltype(__gnu_cxx::__ops::__equal_val(__first, __value)) __comp =
+ __gnu_cxx::__ops::__equal_val(__first, __value);
+ return std::__count_if(__first, __last, __comp);
}
/**
@@ -4082,8 +4148,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
typename iterator_traits<_InputIterator>::value_type>)
__glibcxx_requires_valid_range(__first, __last);
- return std::__count_if(__first, __last,
- __gnu_cxx::__ops::__pred_iter(__pred));
+ return std::__count_if(__first, __last, _GLIBCXX_MOVE(__pred));
}
/**
@@ -4127,8 +4192,9 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first1, __last1);
__glibcxx_requires_valid_range(__first2, __last2);
- return std::__search(__first1, __last1, __first2, __last2,
- __gnu_cxx::__ops::__iter_equal_to_iter());
+ __decltype(__gnu_cxx::__ops::__equal_to(__first1, __first2)) __comp =
+ __gnu_cxx::__ops::__equal_to(__first1, __first2);
+ return std::__search(__first1, __last1, __first2, __last2, __comp);
}
/**
@@ -4158,8 +4224,9 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
typename iterator_traits<_ForwardIterator>::value_type, _Tp>)
__glibcxx_requires_valid_range(__first, __last);
- return std::__search_n(__first, __last, __count,
- __gnu_cxx::__ops::__iter_equals_val(__val));
+ __decltype(__gnu_cxx::__ops::__equal_val(__first, __val)) __comp =
+ __gnu_cxx::__ops::__equal_val(__first, __val);
+ return std::__search_n(__first, __last, __count, __comp);
}
@@ -4194,8 +4261,12 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
typename iterator_traits<_ForwardIterator>::value_type, _Tp>)
__glibcxx_requires_valid_range(__first, __last);
+ __decltype(__gnu_cxx::__ops::__comp_val
+ (_GLIBCXX_MOVE(__binary_pred), __first, __val)) __unry_pred =
+ __gnu_cxx::__ops::__comp_val(_GLIBCXX_MOVE(__binary_pred),
+ __first, __val);
return std::__search_n(__first, __last, __count,
- __gnu_cxx::__ops::__iter_comp_val(__binary_pred, __val));
+ _GLIBCXX_MOVE(__unry_pred));
}
#if __cplusplus >= 201703L
@@ -4451,8 +4522,11 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
if (__first == __last)
return __result;
+
+ __decltype(__gnu_cxx::__ops::__equal_to(__first)) __comp =
+ __gnu_cxx::__ops::__equal_to(__first);
return std::__unique_copy(__first, __last, __result,
- __gnu_cxx::__ops::__iter_equal_to_iter(),
+ __comp,
std::__iterator_category(__first),
std::__iterator_category(__result));
}
@@ -4492,7 +4566,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
if (__first == __last)
return __result;
return std::__unique_copy(__first, __last, __result,
- __gnu_cxx::__ops::__iter_comp_iter(__binary_pred),
+ _GLIBCXX_MOVE(__binary_pred),
std::__iterator_category(__first),
std::__iterator_category(__result));
}
@@ -4632,7 +4706,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
typename iterator_traits<_ForwardIterator>::value_type>)
__glibcxx_requires_valid_range(__first, __last);
- return std::__partition(__first, __last, __pred,
+ return std::__partition(__first, __last, _GLIBCXX_MOVE(__pred),
std::__iterator_category(__first));
}
@@ -4670,8 +4744,9 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__middle, __last);
__glibcxx_requires_irreflexive(__first, __last);
- std::__partial_sort(__first, __middle, __last,
- __gnu_cxx::__ops::__iter_less_iter());
+ __decltype(__gnu_cxx::__ops::__less(__first)) __comp =
+ __gnu_cxx::__ops::__less(__first);
+ std::__partial_sort(__first, __middle, __last, __comp);
}
/**
@@ -4711,8 +4786,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__middle, __last);
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
- std::__partial_sort(__first, __middle, __last,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ std::__partial_sort(__first, __middle, __last, _GLIBCXX_MOVE(__comp));
}
/**
@@ -4748,9 +4822,11 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
if (__first == __last || __nth == __last)
return;
+ __decltype(__gnu_cxx::__ops::__less(__first)) __comp =
+ __gnu_cxx::__ops::__less(__first);
std::__introselect(__first, __nth, __last,
std::__lg(__last - __first) * 2,
- __gnu_cxx::__ops::__iter_less_iter());
+ __comp);
}
/**
@@ -4791,7 +4867,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
std::__introselect(__first, __nth, __last,
std::__lg(__last - __first) * 2,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ _GLIBCXX_MOVE(__comp));
}
/**
@@ -4821,7 +4897,9 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive(__first, __last);
- std::__sort(__first, __last, __gnu_cxx::__ops::__iter_less_iter());
+ __decltype(__gnu_cxx::__ops::__less(__first)) __comp =
+ __gnu_cxx::__ops::__less(__first);
+ std::__sort(__first, __last, __comp);
}
/**
@@ -4854,7 +4932,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
- std::__sort(__first, __last, __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ std::__sort(__first, __last, _GLIBCXX_MOVE(__comp));
}
template<typename _InputIterator1, typename _InputIterator2,
@@ -4863,11 +4941,11 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
_OutputIterator
__merge(_InputIterator1 __first1, _InputIterator1 __last1,
_InputIterator2 __first2, _InputIterator2 __last2,
- _OutputIterator __result, _Compare __comp)
+ _OutputIterator __result, _GLIBCXX_FWDREF(_Compare) __comp)
{
while (__first1 != __last1 && __first2 != __last2)
{
- if (__comp(__first2, __first1))
+ if (__comp(*__first2, *__first1))
{
*__result = *__first2;
++__first2;
@@ -4925,9 +5003,10 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_irreflexive2(__first1, __last1);
__glibcxx_requires_irreflexive2(__first2, __last2);
+ __decltype(__gnu_cxx::__ops::__less(__first1, __first2)) __comp =
+ __gnu_cxx::__ops::__less(__first1, __first2);
return _GLIBCXX_STD_A::__merge(__first1, __last1,
- __first2, __last2, __result,
- __gnu_cxx::__ops::__iter_less_iter());
+ __first2, __last2, __result, __comp);
}
/**
@@ -4977,14 +5056,14 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_irreflexive_pred2(__first2, __last2, __comp);
return _GLIBCXX_STD_A::__merge(__first1, __last1,
- __first2, __last2, __result,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ __first2, __last2, __result,
+ _GLIBCXX_MOVE(__comp));
}
template<typename _RandomAccessIterator, typename _Compare>
inline void
__stable_sort(_RandomAccessIterator __first, _RandomAccessIterator __last,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
typedef typename iterator_traits<_RandomAccessIterator>::value_type
_ValueType;
@@ -5003,14 +5082,18 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
if (__builtin_expect(__buf.requested_size() == __buf.size(), true))
std::__stable_sort_adaptive(__first,
__first + _DistanceType(__buf.size()),
- __last, __buf.begin(), __comp);
+ __last, __buf.begin(),
+ _GLIBCXX_FORWARD(_Compare, __comp));
else if (__builtin_expect(__buf.begin() == 0, false))
- std::__inplace_stable_sort(__first, __last, __comp);
+ std::__inplace_stable_sort(__first, __last,
+ _GLIBCXX_FORWARD(_Compare, __comp));
else
std::__stable_sort_adaptive_resize(__first, __last, __buf.begin(),
- _DistanceType(__buf.size()), __comp);
+ _DistanceType(__buf.size()),
+ _GLIBCXX_FORWARD(_Compare, __comp));
#else
- std::__inplace_stable_sort(__first, __last, __comp);
+ std::__inplace_stable_sort
+ (__first, __last, _GLIBCXX_FORWARD(_Compare, __comp));
#endif
}
@@ -5043,8 +5126,9 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive(__first, __last);
- _GLIBCXX_STD_A::__stable_sort(__first, __last,
- __gnu_cxx::__ops::__iter_less_iter());
+ __decltype(__gnu_cxx::__ops::__less(__first)) __comp =
+ __gnu_cxx::__ops::__less(__first);
+ _GLIBCXX_STD_A::__stable_sort(__first, __last, __comp);
}
/**
@@ -5079,8 +5163,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
- _GLIBCXX_STD_A::__stable_sort(__first, __last,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ _GLIBCXX_STD_A::__stable_sort(__first, __last, _GLIBCXX_MOVE(__comp));
}
template<typename _InputIterator1, typename _InputIterator2,
@@ -5090,16 +5173,16 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
_OutputIterator
__set_union(_InputIterator1 __first1, _InputIterator1 __last1,
_InputIterator2 __first2, _InputIterator2 __last2,
- _OutputIterator __result, _Compare __comp)
+ _OutputIterator __result, _GLIBCXX_FWDREF(_Compare) __comp)
{
while (__first1 != __last1 && __first2 != __last2)
{
- if (__comp(__first1, __first2))
+ if (__comp(*__first1, *__first2))
{
*__result = *__first1;
++__first1;
}
- else if (__comp(__first2, __first1))
+ else if (__comp(*__first2, *__first1))
{
*__result = *__first2;
++__first2;
@@ -5161,9 +5244,10 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_irreflexive2(__first1, __last1);
__glibcxx_requires_irreflexive2(__first2, __last2);
+ __decltype(__gnu_cxx::__ops::__less(__first1, __first2)) __comp =
+ __gnu_cxx::__ops::__less(__first1, __first2);
return _GLIBCXX_STD_A::__set_union(__first1, __last1,
- __first2, __last2, __result,
- __gnu_cxx::__ops::__iter_less_iter());
+ __first2, __last2, __result, __comp);
}
/**
@@ -5213,8 +5297,8 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_irreflexive_pred2(__first2, __last2, __comp);
return _GLIBCXX_STD_A::__set_union(__first1, __last1,
- __first2, __last2, __result,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ __first2, __last2, __result,
+ _GLIBCXX_MOVE(__comp));
}
template<typename _InputIterator1, typename _InputIterator2,
@@ -5224,12 +5308,13 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
_OutputIterator
__set_intersection(_InputIterator1 __first1, _InputIterator1 __last1,
_InputIterator2 __first2, _InputIterator2 __last2,
- _OutputIterator __result, _Compare __comp)
+ _OutputIterator __result,
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
while (__first1 != __last1 && __first2 != __last2)
- if (__comp(__first1, __first2))
+ if (__comp(*__first1, *__first2))
++__first1;
- else if (__comp(__first2, __first1))
+ else if (__comp(*__first2, *__first1))
++__first2;
else
{
@@ -5283,9 +5368,10 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_irreflexive2(__first1, __last1);
__glibcxx_requires_irreflexive2(__first2, __last2);
+ __decltype(__gnu_cxx::__ops::__less(__first1, __first2)) __comp =
+ __gnu_cxx::__ops::__less(__first1, __first2);
return _GLIBCXX_STD_A::__set_intersection(__first1, __last1,
- __first2, __last2, __result,
- __gnu_cxx::__ops::__iter_less_iter());
+ __first2, __last2, __result, __comp);
}
/**
@@ -5334,8 +5420,8 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_irreflexive_pred2(__first2, __last2, __comp);
return _GLIBCXX_STD_A::__set_intersection(__first1, __last1,
- __first2, __last2, __result,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ __first2, __last2, __result,
+ _GLIBCXX_MOVE(__comp));
}
template<typename _InputIterator1, typename _InputIterator2,
@@ -5345,16 +5431,16 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
_OutputIterator
__set_difference(_InputIterator1 __first1, _InputIterator1 __last1,
_InputIterator2 __first2, _InputIterator2 __last2,
- _OutputIterator __result, _Compare __comp)
+ _OutputIterator __result, _GLIBCXX_FWDREF(_Compare) __comp)
{
while (__first1 != __last1 && __first2 != __last2)
- if (__comp(__first1, __first2))
+ if (__comp(*__first1, *__first2))
{
*__result = *__first1;
++__first1;
++__result;
}
- else if (__comp(__first2, __first1))
+ else if (__comp(*__first2, *__first1))
++__first2;
else
{
@@ -5408,9 +5494,10 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_irreflexive2(__first1, __last1);
__glibcxx_requires_irreflexive2(__first2, __last2);
+ __decltype(__gnu_cxx::__ops::__less(__first1, __first2)) __comp =
+ __gnu_cxx::__ops::__less(__first1, __first2);
return _GLIBCXX_STD_A::__set_difference(__first1, __last1,
- __first2, __last2, __result,
- __gnu_cxx::__ops::__iter_less_iter());
+ __first2, __last2, __result, __comp);
}
/**
@@ -5461,8 +5548,8 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_irreflexive_pred2(__first2, __last2, __comp);
return _GLIBCXX_STD_A::__set_difference(__first1, __last1,
- __first2, __last2, __result,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ __first2, __last2, __result,
+ _GLIBCXX_MOVE(__comp));
}
template<typename _InputIterator1, typename _InputIterator2,
@@ -5475,16 +5562,16 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
_InputIterator2 __first2,
_InputIterator2 __last2,
_OutputIterator __result,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
while (__first1 != __last1 && __first2 != __last2)
- if (__comp(__first1, __first2))
+ if (__comp(*__first1, *__first2))
{
*__result = *__first1;
++__first1;
++__result;
}
- else if (__comp(__first2, __first1))
+ else if (__comp(*__first2, *__first1))
{
*__result = *__first2;
++__first2;
@@ -5543,9 +5630,10 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_irreflexive2(__first1, __last1);
__glibcxx_requires_irreflexive2(__first2, __last2);
+ __decltype(__gnu_cxx::__ops::__less(__first1, __first2)) __comp =
+ __gnu_cxx::__ops::__less(__first1, __first2);
return _GLIBCXX_STD_A::__set_symmetric_difference(__first1, __last1,
- __first2, __last2, __result,
- __gnu_cxx::__ops::__iter_less_iter());
+ __first2, __last2, __result, __comp);
}
/**
@@ -5597,21 +5685,21 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_irreflexive_pred2(__first2, __last2, __comp);
return _GLIBCXX_STD_A::__set_symmetric_difference(__first1, __last1,
- __first2, __last2, __result,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ __first2, __last2, __result,
+ _GLIBCXX_MOVE(__comp));
}
template<typename _ForwardIterator, typename _Compare>
_GLIBCXX14_CONSTEXPR
_ForwardIterator
__min_element(_ForwardIterator __first, _ForwardIterator __last,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
if (__first == __last)
return __first;
_ForwardIterator __result = __first;
while (++__first != __last)
- if (__comp(__first, __result))
+ if (__comp(*__first, *__result))
__result = __first;
return __result;
}
@@ -5635,8 +5723,9 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive(__first, __last);
- return _GLIBCXX_STD_A::__min_element(__first, __last,
- __gnu_cxx::__ops::__iter_less_iter());
+ __decltype(__gnu_cxx::__ops::__less(__first)) __comp =
+ __gnu_cxx::__ops::__less(__first);
+ return _GLIBCXX_STD_A::__min_element(__first, __last, __comp);
}
/**
@@ -5663,19 +5752,19 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
return _GLIBCXX_STD_A::__min_element(__first, __last,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ _GLIBCXX_MOVE(__comp));
}
template<typename _ForwardIterator, typename _Compare>
_GLIBCXX14_CONSTEXPR
_ForwardIterator
__max_element(_ForwardIterator __first, _ForwardIterator __last,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
if (__first == __last) return __first;
_ForwardIterator __result = __first;
while (++__first != __last)
- if (__comp(__result, __first))
+ if (__comp(*__result, *__first))
__result = __first;
return __result;
}
@@ -5699,8 +5788,9 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive(__first, __last);
- return _GLIBCXX_STD_A::__max_element(__first, __last,
- __gnu_cxx::__ops::__iter_less_iter());
+ __decltype(__gnu_cxx::__ops::__less(__first)) __comp =
+ __gnu_cxx::__ops::__less(__first);
+ return _GLIBCXX_STD_A::__max_element(__first, __last, __comp);
}
/**
@@ -5727,7 +5817,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
return _GLIBCXX_STD_A::__max_element(__first, __last,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ _GLIBCXX_MOVE(__comp));
}
#if __cplusplus >= 201103L
@@ -5739,7 +5829,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
{
__glibcxx_requires_irreflexive(__l.begin(), __l.end());
return *_GLIBCXX_STD_A::__min_element(__l.begin(), __l.end(),
- __gnu_cxx::__ops::__iter_less_iter());
+ __gnu_cxx::__ops::__less());
}
template<typename _Tp, typename _Compare>
@@ -5749,7 +5839,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
{
__glibcxx_requires_irreflexive_pred(__l.begin(), __l.end(), __comp);
return *_GLIBCXX_STD_A::__min_element(__l.begin(), __l.end(),
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ std::move(__comp));
}
template<typename _Tp>
@@ -5759,7 +5849,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
{
__glibcxx_requires_irreflexive(__l.begin(), __l.end());
return *_GLIBCXX_STD_A::__max_element(__l.begin(), __l.end(),
- __gnu_cxx::__ops::__iter_less_iter());
+ __gnu_cxx::__ops::__less());
}
template<typename _Tp, typename _Compare>
@@ -5769,7 +5859,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
{
__glibcxx_requires_irreflexive_pred(__l.begin(), __l.end(), __comp);
return *_GLIBCXX_STD_A::__max_element(__l.begin(), __l.end(),
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ std::move(__comp));
}
#endif // C++11
diff --git a/libstdc++-v3/include/bits/stl_algobase.h b/libstdc++-v3/include/bits/stl_algobase.h
index 9e92211c124..4496b9a1c46 100644
--- a/libstdc++-v3/include/bits/stl_algobase.h
+++ b/libstdc++-v3/include/bits/stl_algobase.h
@@ -1348,7 +1348,7 @@ _GLIBCXX_END_NAMESPACE_CONTAINER
bool
__lexicographical_compare_impl(_II1 __first1, _II1 __last1,
_II2 __first2, _II2 __last2,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
typedef typename iterator_traits<_II1>::iterator_category _Category1;
typedef typename iterator_traits<_II2>::iterator_category _Category2;
@@ -1358,9 +1358,9 @@ _GLIBCXX_END_NAMESPACE_CONTAINER
for (; __first1 != __last1 && __rai_type::__cnd2(__first2, __last2);
++__first1, (void)++__first2)
{
- if (__comp(__first1, __first2))
+ if (__comp(*__first1, *__first2))
return true;
- if (__comp(__first2, __first1))
+ if (__comp(*__first2, *__first1))
return false;
}
return __first1 == __last1 && __first2 != __last2;
@@ -1374,10 +1374,11 @@ _GLIBCXX_END_NAMESPACE_CONTAINER
static bool
__lc(_II1 __first1, _II1 __last1, _II2 __first2, _II2 __last2)
{
- using __gnu_cxx::__ops::__iter_less_iter;
+ __decltype(__gnu_cxx::__ops::__less(__first1, __first2)) __comp =
+ __gnu_cxx::__ops::__less(__first1, __first2);
return std::__lexicographical_compare_impl(__first1, __last1,
__first2, __last2,
- __iter_less_iter());
+ __comp);
}
template<typename _II1, typename _II2>
@@ -1521,7 +1522,7 @@ _GLIBCXX_END_NAMESPACE_CONTAINER
_GLIBCXX20_CONSTEXPR
_ForwardIterator
__lower_bound(_ForwardIterator __first, _ForwardIterator __last,
- const _Tp& __val, _Compare __comp)
+ const _Tp& __val, _GLIBCXX_FWDREF(_Compare) __comp)
{
typedef typename iterator_traits<_ForwardIterator>::difference_type
_DistanceType;
@@ -1533,7 +1534,7 @@ _GLIBCXX_END_NAMESPACE_CONTAINER
_DistanceType __half = __len >> 1;
_ForwardIterator __middle = __first;
std::advance(__middle, __half);
- if (__comp(__middle, __val))
+ if (__comp(*__middle, __val))
{
__first = __middle;
++__first;
@@ -1568,8 +1569,9 @@ _GLIBCXX_END_NAMESPACE_CONTAINER
typename iterator_traits<_ForwardIterator>::value_type, _Tp>)
__glibcxx_requires_partitioned_lower(__first, __last, __val);
- return std::__lower_bound(__first, __last, __val,
- __gnu_cxx::__ops::__iter_less_val());
+ __decltype(__gnu_cxx::__ops::__less_val(__first, __val)) __comp =
+ __gnu_cxx::__ops::__less_val(__first, __val);
+ return std::__lower_bound(__first, __last, __val, __comp);
}
/// This is a helper function for the sort routines and for random.tcc.
@@ -1688,7 +1690,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
_GLIBCXX20_CONSTEXPR
inline bool
__equal4(_II1 __first1, _II1 __last1, _II2 __first2, _II2 __last2,
- _BinaryPredicate __binary_pred)
+ _BinaryPredicate&& __binary_pred)
{
using _RATag = random_access_iterator_tag;
using _Cat1 = typename iterator_traits<_II1>::iterator_category;
@@ -1701,7 +1703,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
if (__d1 != __d2)
return false;
return _GLIBCXX_STD_A::equal(__first1, __last1, __first2,
- __binary_pred);
+ std::forward<_BinaryPredicate>(__binary_pred));
}
for (; __first1 != __last1 && __first2 != __last2;
@@ -1772,7 +1774,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first2, __last2);
return _GLIBCXX_STD_A::__equal4(__first1, __last1, __first2, __last2,
- __binary_pred);
+ std::move(__binary_pred));
}
#endif // __glibcxx_robust_nonmodifying_seq_ops
@@ -1839,8 +1841,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first2, __last2);
return std::__lexicographical_compare_impl
- (__first1, __last1, __first2, __last2,
- __gnu_cxx::__ops::__iter_comp_iter(__comp));
+ (__first1, __last1, __first2, __last2, _GLIBCXX_MOVE(__comp));
}
#if __cpp_lib_three_way_comparison
@@ -1946,9 +1947,10 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
_GLIBCXX20_CONSTEXPR
pair<_InputIterator1, _InputIterator2>
__mismatch(_InputIterator1 __first1, _InputIterator1 __last1,
- _InputIterator2 __first2, _BinaryPredicate __binary_pred)
+ _InputIterator2 __first2,
+ _GLIBCXX_FWDREF(_BinaryPredicate) __binary_pred)
{
- while (__first1 != __last1 && __binary_pred(__first1, __first2))
+ while (__first1 != __last1 && __binary_pred(*__first1, *__first2))
{
++__first1;
++__first2;
@@ -1983,8 +1985,9 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
typename iterator_traits<_InputIterator2>::value_type>)
__glibcxx_requires_valid_range(__first1, __last1);
- return _GLIBCXX_STD_A::__mismatch(__first1, __last1, __first2,
- __gnu_cxx::__ops::__iter_equal_to_iter());
+ __decltype(__gnu_cxx::__ops::__equal_to(__first1, __first2)) __comp =
+ __gnu_cxx::__ops::__equal_to(__first1, __first2);
+ return _GLIBCXX_STD_A::__mismatch(__first1, __last1, __first2, __comp);
}
/**
@@ -2016,7 +2019,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first1, __last1);
return _GLIBCXX_STD_A::__mismatch(__first1, __last1, __first2,
- __gnu_cxx::__ops::__iter_comp_iter(__binary_pred));
+ _GLIBCXX_MOVE(__binary_pred));
}
#if __glibcxx_robust_nonmodifying_seq_ops // C++ >= 14
@@ -2026,10 +2029,10 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
pair<_InputIterator1, _InputIterator2>
__mismatch(_InputIterator1 __first1, _InputIterator1 __last1,
_InputIterator2 __first2, _InputIterator2 __last2,
- _BinaryPredicate __binary_pred)
+ _BinaryPredicate&& __binary_pred)
{
while (__first1 != __last1 && __first2 != __last2
- && __binary_pred(__first1, __first2))
+ && __binary_pred(*__first1, *__first2))
{
++__first1;
++__first2;
@@ -2067,7 +2070,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first2, __last2);
return _GLIBCXX_STD_A::__mismatch(__first1, __last1, __first2, __last2,
- __gnu_cxx::__ops::__iter_equal_to_iter());
+ __gnu_cxx::__ops::__equal_to(__first1, __first2));
}
/**
@@ -2102,7 +2105,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first2, __last2);
return _GLIBCXX_STD_A::__mismatch(__first1, __last1, __first2, __last2,
- __gnu_cxx::__ops::__iter_comp_iter(__binary_pred));
+ _GLIBCXX_MOVE(__binary_pred));
}
#endif
@@ -2112,10 +2115,11 @@ _GLIBCXX_END_NAMESPACE_ALGO
template<typename _Iterator, typename _Predicate>
_GLIBCXX20_CONSTEXPR
inline _Iterator
- __find_if(_Iterator __first, _Iterator __last, _Predicate __pred)
+ __find_if(_Iterator __first, _Iterator __last,
+ _GLIBCXX_FWDREF(_Predicate) __pred)
{
#pragma GCC unroll 4
- while (__first != __last && !__pred(__first))
+ while (__first != __last && !__pred(*__first))
++__first;
return __first;
}
@@ -2123,11 +2127,12 @@ _GLIBCXX_END_NAMESPACE_ALGO
template<typename _InputIterator, typename _Predicate>
_GLIBCXX20_CONSTEXPR
typename iterator_traits<_InputIterator>::difference_type
- __count_if(_InputIterator __first, _InputIterator __last, _Predicate __pred)
+ __count_if(_InputIterator __first, _InputIterator __last,
+ _GLIBCXX_FWDREF(_Predicate) __pred)
{
typename iterator_traits<_InputIterator>::difference_type __n = 0;
for (; __first != __last; ++__first)
- if (__pred(__first))
+ if (__pred(*__first))
++__n;
return __n;
}
@@ -2136,7 +2141,7 @@ _GLIBCXX_END_NAMESPACE_ALGO
_GLIBCXX20_CONSTEXPR
_ForwardIterator
__remove_if(_ForwardIterator __first, _ForwardIterator __last,
- _Predicate __pred)
+ _GLIBCXX_FWDREF(_Predicate) __pred)
{
__first = std::__find_if(__first, __last, __pred);
if (__first == __last)
@@ -2144,7 +2149,7 @@ _GLIBCXX_END_NAMESPACE_ALGO
_ForwardIterator __result = __first;
++__first;
for (; __first != __last; ++__first)
- if (!__pred(__first))
+ if (!__pred(*__first))
{
*__result = _GLIBCXX_MOVE(*__first);
++__result;
@@ -2158,7 +2163,7 @@ _GLIBCXX_END_NAMESPACE_ALGO
_ForwardIterator1
__search(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
_ForwardIterator2 __first2, _ForwardIterator2 __last2,
- _BinaryPredicate __predicate)
+ _GLIBCXX_FWDREF(_BinaryPredicate) __predicate)
{
// Test for empty ranges
if (__first1 == __last1 || __first2 == __last2)
@@ -2167,18 +2172,25 @@ _GLIBCXX_END_NAMESPACE_ALGO
// Test for a pattern of length 1.
_ForwardIterator2 __p1(__first2);
if (++__p1 == __last2)
- return std::__find_if(__first1, __last1,
- __gnu_cxx::__ops::__iter_comp_iter(__predicate, __first2));
+ {
+ __decltype(__gnu_cxx::__ops::__equal_ite
+ (_GLIBCXX_FORWARD(_BinaryPredicate, __predicate),
+ __first1, __first2)) __cmp =
+ __gnu_cxx::__ops::__equal_ite
+ (_GLIBCXX_FORWARD(_BinaryPredicate, __predicate),
+ __first1, __first2);
+ return std::__find_if(__first1, __last1, _GLIBCXX_MOVE(__cmp));
+ }
// General case.
_ForwardIterator1 __current = __first1;
+ __decltype(__gnu_cxx::__ops::__equal_ite(__predicate, __first1, __first2))
+ __unry_pred = __gnu_cxx::__ops::__equal_ite(__predicate,
+ __first1, __first2);
for (;;)
{
- __first1 =
- std::__find_if(__first1, __last1,
- __gnu_cxx::__ops::__iter_comp_iter(__predicate, __first2));
-
+ __first1 = std::__find_if(__first1, __last1, __unry_pred);
if (__first1 == __last1)
return __last1;
@@ -2187,7 +2199,7 @@ _GLIBCXX_END_NAMESPACE_ALGO
if (++__current == __last1)
return __last1;
- while (__predicate(__current, __p))
+ while (__predicate(*__current, *__p))
{
if (++__p == __last2)
return __first1;
@@ -2210,7 +2222,7 @@ _GLIBCXX_END_NAMESPACE_ALGO
// Efficiently compare identical prefixes: O(N) if sequences
// have the same elements in the same order.
for (; __first1 != __last1; ++__first1, (void)++__first2)
- if (!__pred(__first1, __first2))
+ if (!__pred(*__first1, *__first2))
break;
if (__first1 == __last1)
@@ -2223,15 +2235,15 @@ _GLIBCXX_END_NAMESPACE_ALGO
for (_ForwardIterator1 __scan = __first1; __scan != __last1; ++__scan)
{
if (__scan != std::__find_if(__first1, __scan,
- __gnu_cxx::__ops::__iter_comp_iter(__pred, __scan)))
+ __gnu_cxx::__ops::__equal_ite(__pred, __first1, __scan)))
continue; // We've seen this one before.
auto __matches
= std::__count_if(__first2, __last2,
- __gnu_cxx::__ops::__iter_comp_iter(__pred, __scan));
+ __gnu_cxx::__ops::__equal_ite(__pred, __first2, __scan));
if (0 == __matches ||
std::__count_if(__scan, __last1,
- __gnu_cxx::__ops::__iter_comp_iter(__pred, __scan))
+ __gnu_cxx::__ops::__equal_ite(__pred, __first1, __scan))
!= __matches)
return false;
}
@@ -2265,7 +2277,7 @@ _GLIBCXX_END_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first1, __last1);
return std::__is_permutation(__first1, __last1, __first2,
- __gnu_cxx::__ops::__iter_equal_to_iter());
+ __gnu_cxx::__ops::__equal_to());
}
#endif // C++11
@@ -2310,7 +2322,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO
__glibcxx_requires_valid_range(__first2, __last2);
return std::__search(__first1, __last1, __first2, __last2,
- __gnu_cxx::__ops::__iter_comp_iter(__predicate));
+ _GLIBCXX_MOVE(__predicate));
}
_GLIBCXX_END_NAMESPACE_ALGO
diff --git a/libstdc++-v3/include/bits/stl_heap.h b/libstdc++-v3/include/bits/stl_heap.h
index 9c1214a2b21..d499d15f517 100644
--- a/libstdc++-v3/include/bits/stl_heap.h
+++ b/libstdc++-v3/include/bits/stl_heap.h
@@ -74,12 +74,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX20_CONSTEXPR
_Distance
__is_heap_until(_RandomAccessIterator __first, _Distance __n,
- _Compare& __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
_Distance __parent = 0;
for (_Distance __child = 1; __child < __n; ++__child)
{
- if (__comp(__first + __parent, __first + __child))
+ if (__comp(__first[__parent], __first[__child]))
return __child;
if ((__child & 1) == 0)
++__parent;
@@ -94,7 +94,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
inline bool
__is_heap(_RandomAccessIterator __first, _Distance __n)
{
- __gnu_cxx::__ops::_Iter_less_iter __comp;
+ __decltype(__gnu_cxx::__ops::__less(__first)) __comp =
+ __gnu_cxx::__ops::__less(__first);
return std::__is_heap_until(__first, __n, __comp) == __n;
}
@@ -102,11 +103,11 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
typename _Distance>
_GLIBCXX20_CONSTEXPR
inline bool
- __is_heap(_RandomAccessIterator __first, _Compare __comp, _Distance __n)
+ __is_heap(_RandomAccessIterator __first, _GLIBCXX_FWDREF(_Compare) __comp,
+ _Distance __n)
{
- typedef __decltype(__comp) _Cmp;
- __gnu_cxx::__ops::_Iter_comp_iter<_Cmp> __cmp(_GLIBCXX_MOVE(__comp));
- return std::__is_heap_until(__first, __n, __cmp) == __n;
+ return std::__is_heap_until
+ (__first, __n, _GLIBCXX_FORWARD(_Compare, __comp)) == __n;
}
template<typename _RandomAccessIterator>
@@ -119,9 +120,9 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX20_CONSTEXPR
inline bool
__is_heap(_RandomAccessIterator __first, _RandomAccessIterator __last,
- _Compare __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
- return std::__is_heap(__first, _GLIBCXX_MOVE(__comp),
+ return std::__is_heap(__first, _GLIBCXX_FORWARD(_Compare, __comp),
std::distance(__first, __last));
}
@@ -133,17 +134,22 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX20_CONSTEXPR
void
__push_heap(_RandomAccessIterator __first,
- _Distance __holeIndex, _Distance __topIndex, _Tp __value,
- _Compare& __comp)
+ _Distance __holeIndex, _Distance __topIndex,
+#if __cplusplus >= 201103L
+ _Tp&& __value,
+#else
+ _Tp __value,
+#endif
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
_Distance __parent = (__holeIndex - 1) / 2;
- while (__holeIndex > __topIndex && __comp(__first + __parent, __value))
+ while (__holeIndex > __topIndex && __comp(__first[__parent], __value))
{
*(__first + __holeIndex) = _GLIBCXX_MOVE(*(__first + __parent));
__holeIndex = __parent;
__parent = (__holeIndex - 1) / 2;
}
- *(__first + __holeIndex) = _GLIBCXX_MOVE(__value);
+ *(__first + __holeIndex) = _GLIBCXX_FORWARD(_Tp, __value);
}
/**
@@ -174,8 +180,9 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__glibcxx_requires_irreflexive(__first, __last);
__glibcxx_requires_heap(__first, __last - 1);
- __gnu_cxx::__ops::_Iter_less_val __comp;
_ValueType __value = _GLIBCXX_MOVE(*(__last - 1));
+ __decltype(__gnu_cxx::__ops::__less_val(__first, __value)) __comp =
+ __gnu_cxx::__ops::__less_val(__first, __value);
std::__push_heap(__first, _DistanceType((__last - __first) - 1),
_DistanceType(0), _GLIBCXX_MOVE(__value), __comp);
}
@@ -210,11 +217,10 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
__glibcxx_requires_heap_pred(__first, __last - 1, __comp);
- __decltype(__gnu_cxx::__ops::__iter_comp_val(_GLIBCXX_MOVE(__comp)))
- __cmp(_GLIBCXX_MOVE(__comp));
_ValueType __value = _GLIBCXX_MOVE(*(__last - 1));
std::__push_heap(__first, _DistanceType((__last - __first) - 1),
- _DistanceType(0), _GLIBCXX_MOVE(__value), __cmp);
+ _DistanceType(0), _GLIBCXX_MOVE(__value),
+ _GLIBCXX_MOVE(__comp));
}
template<typename _RandomAccessIterator, typename _Distance,
@@ -222,15 +228,21 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX20_CONSTEXPR
void
__adjust_heap(_RandomAccessIterator __first, _Distance __holeIndex,
- _Distance __len, _Tp __value, _Compare __comp)
+ _Distance __len,
+#if __cplusplus >= 201103L
+ _Tp&& __value,
+#else
+ _Tp __value,
+#endif
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
const _Distance __topIndex = __holeIndex;
_Distance __secondChild = __holeIndex;
while (__secondChild < (__len - 1) / 2)
{
__secondChild = 2 * (__secondChild + 1);
- if (__comp(__first + __secondChild,
- __first + (__secondChild - 1)))
+ if (__comp(__first[__secondChild],
+ __first[__secondChild - 1]))
__secondChild--;
*(__first + __holeIndex) = _GLIBCXX_MOVE(*(__first + __secondChild));
__holeIndex = __secondChild;
@@ -242,17 +254,20 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
+ (__secondChild - 1)));
__holeIndex = __secondChild - 1;
}
- __decltype(__gnu_cxx::__ops::__iter_comp_val(_GLIBCXX_MOVE(__comp)))
- __cmp(_GLIBCXX_MOVE(__comp));
+ __decltype(__gnu_cxx::__ops::__less_val(_GLIBCXX_FORWARD(_Compare, __comp),
+ __first, __value)) __cmp =
+ __gnu_cxx::__ops::__less_val(_GLIBCXX_FORWARD(_Compare, __comp),
+ __first, __value);
std::__push_heap(__first, __holeIndex, __topIndex,
- _GLIBCXX_MOVE(__value), __cmp);
+ _GLIBCXX_FORWARD(_Tp, __value),
+ _GLIBCXX_FORWARD(_Compare, __cmp));
}
template<typename _RandomAccessIterator, typename _Compare>
_GLIBCXX20_CONSTEXPR
inline void
__pop_heap(_RandomAccessIterator __first, _RandomAccessIterator __last,
- _RandomAccessIterator __result, _Compare& __comp)
+ _RandomAccessIterator __result, _GLIBCXX_FWDREF(_Compare) __comp)
{
typedef typename iterator_traits<_RandomAccessIterator>::value_type
_ValueType;
@@ -263,7 +278,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
*__result = _GLIBCXX_MOVE(*__first);
std::__adjust_heap(__first, _DistanceType(0),
_DistanceType(__last - __first),
- _GLIBCXX_MOVE(__value), __comp);
+ _GLIBCXX_MOVE(__value), _GLIBCXX_FORWARD(_Compare, __comp));
}
/**
@@ -295,7 +310,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
if (__last - __first > 1)
{
--__last;
- __gnu_cxx::__ops::_Iter_less_iter __comp;
+ __decltype(__gnu_cxx::__ops::__less(__first)) __comp =
+ __gnu_cxx::__ops::__less(__first);
std::__pop_heap(__first, __last, __last, __comp);
}
}
@@ -327,10 +343,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
if (__last - __first > 1)
{
- typedef __decltype(__comp) _Cmp;
- __gnu_cxx::__ops::_Iter_comp_iter<_Cmp> __cmp(_GLIBCXX_MOVE(__comp));
--__last;
- std::__pop_heap(__first, __last, __last, __cmp);
+ std::__pop_heap(__first, __last, __last, _GLIBCXX_MOVE(__comp));
}
}
@@ -338,7 +352,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_GLIBCXX20_CONSTEXPR
void
__make_heap(_RandomAccessIterator __first, _RandomAccessIterator __last,
- _Compare& __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
typedef typename iterator_traits<_RandomAccessIterator>::value_type
_ValueType;
@@ -382,7 +396,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive(__first, __last);
- __gnu_cxx::__ops::_Iter_less_iter __comp;
+ __decltype(__gnu_cxx::__ops::__less(__first)) __comp =
+ __gnu_cxx::__ops::__less(__first);
std::__make_heap(__first, __last, __comp);
}
@@ -408,16 +423,14 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
- typedef __decltype(__comp) _Cmp;
- __gnu_cxx::__ops::_Iter_comp_iter<_Cmp> __cmp(_GLIBCXX_MOVE(__comp));
- std::__make_heap(__first, __last, __cmp);
+ std::__make_heap(__first, __last, _GLIBCXX_MOVE(__comp));
}
template<typename _RandomAccessIterator, typename _Compare>
_GLIBCXX20_CONSTEXPR
void
__sort_heap(_RandomAccessIterator __first, _RandomAccessIterator __last,
- _Compare& __comp)
+ _GLIBCXX_FWDREF(_Compare) __comp)
{
while (__last - __first > 1)
{
@@ -448,7 +461,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__glibcxx_requires_irreflexive(__first, __last);
__glibcxx_requires_heap(__first, __last);
- __gnu_cxx::__ops::_Iter_less_iter __comp;
+ __decltype(__gnu_cxx::__ops::__less(__first)) __comp =
+ __gnu_cxx::__ops::__less(__first);
std::__sort_heap(__first, __last, __comp);
}
@@ -475,9 +489,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
__glibcxx_requires_heap_pred(__first, __last, __comp);
- typedef __decltype(__comp) _Cmp;
- __gnu_cxx::__ops::_Iter_comp_iter<_Cmp> __cmp(_GLIBCXX_MOVE(__comp));
- std::__sort_heap(__first, __last, __cmp);
+ std::__sort_heap(__first, __last, _GLIBCXX_MOVE(__comp));
}
#if __cplusplus >= 201103L
@@ -504,9 +516,9 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive(__first, __last);
- __gnu_cxx::__ops::_Iter_less_iter __comp;
return __first +
- std::__is_heap_until(__first, std::distance(__first, __last), __comp);
+ std::__is_heap_until(__first, std::distance(__first, __last),
+ __gnu_cxx::__ops::__less());
}
/**
@@ -532,10 +544,9 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__glibcxx_requires_valid_range(__first, __last);
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
- typedef __decltype(__comp) _Cmp;
- __gnu_cxx::__ops::_Iter_comp_iter<_Cmp> __cmp(_GLIBCXX_MOVE(__comp));
return __first
- + std::__is_heap_until(__first, std::distance(__first, __last), __cmp);
+ + std::__is_heap_until(__first, std::distance(__first, __last),
+ std::move(__comp));
}
/**
@@ -572,11 +583,10 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
__glibcxx_requires_irreflexive_pred(__first, __last, __comp);
const auto __dist = std::distance(__first, __last);
- typedef __decltype(__comp) _Cmp;
- __gnu_cxx::__ops::_Iter_comp_iter<_Cmp> __cmp(_GLIBCXX_MOVE(__comp));
- return std::__is_heap_until(__first, __dist, __cmp) == __dist;
+ return std::__is_heap_until(__first, __dist,
+ std::move(__comp)) == __dist;
}
-#endif
+#endif // C++11
_GLIBCXX_END_NAMESPACE_VERSION
} // namespace
diff --git a/libstdc++-v3/include/bits/stl_tree.h b/libstdc++-v3/include/bits/stl_tree.h
index bc27e191e8b..8338a4d7acb 100644
--- a/libstdc++-v3/include/bits/stl_tree.h
+++ b/libstdc++-v3/include/bits/stl_tree.h
@@ -463,7 +463,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
template<typename _Arg>
_Link_type
- operator()(_GLIBCXX_FWDREF(_Arg) __arg)
+ operator()(_GLIBCXX_FWDCREF(_Arg) __arg)
{
_Link_type __node = static_cast<_Link_type>(_M_extract());
if (__node)
@@ -525,7 +525,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
template<typename _Arg>
_Link_type
- operator()(_GLIBCXX_FWDREF(_Arg) __arg) const
+ operator()(_GLIBCXX_FWDCREF(_Arg) __arg) const
{ return _M_t._M_create_node(_GLIBCXX_FORWARD(_Arg, __arg)); }
private:
diff --git a/libstdc++-v3/include/std/deque b/libstdc++-v3/include/std/deque
index 33396d180c8..924db7f37bc 100644
--- a/libstdc++-v3/include/std/deque
+++ b/libstdc++-v3/include/std/deque
@@ -66,7 +66,7 @@
#include <bits/stl_construct.h>
#include <bits/stl_uninitialized.h>
#include <bits/stl_deque.h>
-#include <bits/refwrap.h>
+#include <bits/move.h>
#include <bits/range_access.h>
#include <bits/deque.tcc>
@@ -103,12 +103,11 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
inline typename deque<_Tp, _Alloc>::size_type
erase_if(deque<_Tp, _Alloc>& __cont, _Predicate __pred)
{
- using namespace __gnu_cxx;
_GLIBCXX_STD_C::deque<_Tp, _Alloc>& __ucont = __cont;
const auto __osz = __cont.size();
const auto __end = __ucont.end();
auto __removed = std::__remove_if(__ucont.begin(), __end,
- __ops::__pred_iter(std::ref(__pred)));
+ std::move(__pred));
if (__removed != __end)
{
__cont.erase(__niter_wrap(__cont.begin(), __removed),
@@ -129,7 +128,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
const auto __osz = __cont.size();
const auto __end = __ucont.end();
auto __removed = std::__remove_if(__ucont.begin(), __end,
- __ops::__iter_equals_val(__value));
+ __ops::__equal_val(__value));
if (__removed != __end)
{
__cont.erase(__niter_wrap(__cont.begin(), __removed),
diff --git a/libstdc++-v3/include/std/functional b/libstdc++-v3/include/std/functional
index 743defc3cb8..e830d1e28d0 100644
--- a/libstdc++-v3/include/std/functional
+++ b/libstdc++-v3/include/std/functional
@@ -60,6 +60,9 @@
#if _GLIBCXX_HOSTED
# include <bits/std_function.h> // std::function
#endif
+#if __cplusplus >= 201402L
+# include <bits/predefined_ops.h> // std::_Not_fn
+#endif
#if __cplusplus >= 201703L
# if _GLIBCXX_HOSTED
# include <unordered_map>
@@ -1119,57 +1122,6 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
#endif // __cpp_lib_bind_back
#if __cplusplus >= 201402L
- /// Generalized negator.
- template<typename _Fn>
- class _Not_fn
- {
- template<typename _Fn2, typename... _Args>
- using __inv_res_t = typename __invoke_result<_Fn2, _Args...>::type;
-
- template<typename _Tp>
- static decltype(!std::declval<_Tp>())
- _S_not() noexcept(noexcept(!std::declval<_Tp>()));
-
- public:
- template<typename _Fn2>
- constexpr
- _Not_fn(_Fn2&& __fn, int)
- : _M_fn(std::forward<_Fn2>(__fn)) { }
-
- _Not_fn(const _Not_fn& __fn) = default;
- _Not_fn(_Not_fn&& __fn) = default;
- ~_Not_fn() = default;
-
- // Macro to define operator() with given cv-qualifiers ref-qualifiers,
- // forwarding _M_fn and the function arguments with the same qualifiers,
- // and deducing the return type and exception-specification.
-#define _GLIBCXX_NOT_FN_CALL_OP( _QUALS ) \
- template<typename... _Args, \
- typename = enable_if_t<__is_invocable<_Fn _QUALS, _Args...>::value>> \
- _GLIBCXX20_CONSTEXPR \
- decltype(_S_not<__inv_res_t<_Fn _QUALS, _Args...>>()) \
- operator()(_Args&&... __args) _QUALS \
- noexcept(__is_nothrow_invocable<_Fn _QUALS, _Args...>::value \
- && noexcept(_S_not<__inv_res_t<_Fn _QUALS, _Args...>>())) \
- { \
- return !std::__invoke(std::forward< _Fn _QUALS >(_M_fn), \
- std::forward<_Args>(__args)...); \
- } \
- \
- template<typename... _Args, \
- typename = enable_if_t<!__is_invocable<_Fn _QUALS, _Args...>::value>> \
- void operator()(_Args&&... __args) _QUALS = delete;
-
- _GLIBCXX_NOT_FN_CALL_OP( & )
- _GLIBCXX_NOT_FN_CALL_OP( const & )
- _GLIBCXX_NOT_FN_CALL_OP( && )
- _GLIBCXX_NOT_FN_CALL_OP( const && )
-#undef _GLIBCXX_NOT_FN_CALL_OP
-
- private:
- _Fn _M_fn;
- };
-
template<typename _Tp, typename _Pred>
struct __is_byte_like : false_type { };
diff --git a/libstdc++-v3/include/std/string b/libstdc++-v3/include/std/string
index fd69e9cb746..319795870a6 100644
--- a/libstdc++-v3/include/std/string
+++ b/libstdc++-v3/include/std/string
@@ -51,7 +51,7 @@
#include <bits/stl_function.h> // For less
#include <ext/numeric_traits.h>
#include <bits/stl_algobase.h>
-#include <bits/refwrap.h>
+#include <bits/move.h>
#include <bits/range_access.h>
#include <bits/basic_string.h>
#include <bits/basic_string.tcc>
@@ -99,11 +99,10 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
inline typename basic_string<_CharT, _Traits, _Alloc>::size_type
erase_if(basic_string<_CharT, _Traits, _Alloc>& __cont, _Predicate __pred)
{
- using namespace __gnu_cxx;
const auto __osz = __cont.size();
const auto __end = __cont.end();
auto __removed = std::__remove_if(__cont.begin(), __end,
- __ops::__pred_iter(std::ref(__pred)));
+ std::move(__pred));
__cont.erase(__removed, __end);
return __osz - __cont.size();
}
@@ -118,7 +117,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
const auto __osz = __cont.size();
const auto __end = __cont.end();
auto __removed = std::__remove_if(__cont.begin(), __end,
- __ops::__iter_equals_val(__value));
+ __ops::__equal_val(__value));
__cont.erase(__removed, __end);
return __osz - __cont.size();
}
diff --git a/libstdc++-v3/include/std/vector b/libstdc++-v3/include/std/vector
index 705bcdc9c08..56e0d207139 100644
--- a/libstdc++-v3/include/std/vector
+++ b/libstdc++-v3/include/std/vector
@@ -67,7 +67,7 @@
#include <bits/stl_uninitialized.h>
#include <bits/stl_vector.h>
#include <bits/stl_bvector.h>
-#include <bits/refwrap.h>
+#include <bits/move.h>
#include <bits/range_access.h>
#ifndef _GLIBCXX_EXPORT_TEMPLATE
@@ -116,12 +116,11 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
inline typename vector<_Tp, _Alloc>::size_type
erase_if(vector<_Tp, _Alloc>& __cont, _Predicate __pred)
{
- using namespace __gnu_cxx;
_GLIBCXX_STD_C::vector<_Tp, _Alloc>& __ucont = __cont;
const auto __osz = __cont.size();
const auto __end = __ucont.end();
auto __removed = std::__remove_if(__ucont.begin(), __end,
- __ops::__pred_iter(std::ref(__pred)));
+ std::move(__pred));
if (__removed != __end)
{
__cont.erase(__niter_wrap(__cont.begin(), __removed),
@@ -143,7 +142,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
const auto __osz = __cont.size();
const auto __end = __ucont.end();
auto __removed = std::__remove_if(__ucont.begin(), __end,
- __ops::__iter_equals_val(__value));
+ __ops::__equal_val(__value));
if (__removed != __end)
{
__cont.erase(__niter_wrap(__cont.begin(), __removed),
diff --git a/libstdc++-v3/src/c++17/memory_resource.cc b/libstdc++-v3/src/c++17/memory_resource.cc
index f9958c690f8..86bae3e3d7c 100644
--- a/libstdc++-v3/src/c++17/memory_resource.cc
+++ b/libstdc++-v3/src/c++17/memory_resource.cc
@@ -26,6 +26,7 @@
#include <algorithm> // lower_bound, rotate
#include <atomic>
#include <bit> // has_single_bit, bit_ceil, bit_width
+#include <functional> // less_equal
#include <new>
#include <bits/move.h> // std::__exchange
#if ATOMIC_POINTER_LOCK_FREE != 2
diff --git a/libstdc++-v3/testsuite/25_algorithms/inplace_merge/1.cc b/libstdc++-v3/testsuite/25_algorithms/inplace_merge/1.cc
index c9f1839f731..81270f05cef 100644
--- a/libstdc++-v3/testsuite/25_algorithms/inplace_merge/1.cc
+++ b/libstdc++-v3/testsuite/25_algorithms/inplace_merge/1.cc
@@ -21,6 +21,7 @@
// { dg-require-effective-target hosted }
#include <algorithm>
+#include <vector>
#include <testsuite_hooks.h>
#include <testsuite_iterators.h>
#include <testsuite_new_operators.h>
@@ -119,6 +120,17 @@ test4()
}
}
+bool bs[] = { false, false, true, false, true, true };
+std::vector<bool> v(6);
+
+void
+test5()
+{
+ v.assign(bs, bs + 6);
+ inplace_merge(v.begin(), v.begin() + 3, v.end());
+ VERIFY( !v[0] && !v[1] && !v[2] && v[3] && v[4] && v[5] );
+}
+
int
main()
{
@@ -129,14 +141,17 @@ main()
__gnu_test::set_new_limit(sizeof(S) * 4);
test3();
test4();
+ test5();
__gnu_test::set_new_limit(sizeof(S));
test3();
test4();
+ test5();
__gnu_test::set_new_limit(0);
test3();
test4();
+ test5();
return 0;
}
More information about the Libstdc++
mailing list