xref: /dflybsd-src/contrib/gcc-8.0/libstdc++-v3/include/bits/stl_algo.h (revision 38fd149817dfbff97799f62fcb70be98c4e32523)
1*38fd1498Szrj // Algorithm implementation -*- C++ -*-
2*38fd1498Szrj 
3*38fd1498Szrj // Copyright (C) 2001-2018 Free Software Foundation, Inc.
4*38fd1498Szrj //
5*38fd1498Szrj // This file is part of the GNU ISO C++ Library.  This library is free
6*38fd1498Szrj // software; you can redistribute it and/or modify it under the
7*38fd1498Szrj // terms of the GNU General Public License as published by the
8*38fd1498Szrj // Free Software Foundation; either version 3, or (at your option)
9*38fd1498Szrj // any later version.
10*38fd1498Szrj 
11*38fd1498Szrj // This library is distributed in the hope that it will be useful,
12*38fd1498Szrj // but WITHOUT ANY WARRANTY; without even the implied warranty of
13*38fd1498Szrj // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14*38fd1498Szrj // GNU General Public License for more details.
15*38fd1498Szrj 
16*38fd1498Szrj // Under Section 7 of GPL version 3, you are granted additional
17*38fd1498Szrj // permissions described in the GCC Runtime Library Exception, version
18*38fd1498Szrj // 3.1, as published by the Free Software Foundation.
19*38fd1498Szrj 
20*38fd1498Szrj // You should have received a copy of the GNU General Public License and
21*38fd1498Szrj // a copy of the GCC Runtime Library Exception along with this program;
22*38fd1498Szrj // see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
23*38fd1498Szrj // <http://www.gnu.org/licenses/>.
24*38fd1498Szrj 
25*38fd1498Szrj /*
26*38fd1498Szrj  *
27*38fd1498Szrj  * Copyright (c) 1994
28*38fd1498Szrj  * Hewlett-Packard Company
29*38fd1498Szrj  *
30*38fd1498Szrj  * Permission to use, copy, modify, distribute and sell this software
31*38fd1498Szrj  * and its documentation for any purpose is hereby granted without fee,
32*38fd1498Szrj  * provided that the above copyright notice appear in all copies and
33*38fd1498Szrj  * that both that copyright notice and this permission notice appear
34*38fd1498Szrj  * in supporting documentation.  Hewlett-Packard Company makes no
35*38fd1498Szrj  * representations about the suitability of this software for any
36*38fd1498Szrj  * purpose.  It is provided "as is" without express or implied warranty.
37*38fd1498Szrj  *
38*38fd1498Szrj  *
39*38fd1498Szrj  * Copyright (c) 1996
40*38fd1498Szrj  * Silicon Graphics Computer Systems, Inc.
41*38fd1498Szrj  *
42*38fd1498Szrj  * Permission to use, copy, modify, distribute and sell this software
43*38fd1498Szrj  * and its documentation for any purpose is hereby granted without fee,
44*38fd1498Szrj  * provided that the above copyright notice appear in all copies and
45*38fd1498Szrj  * that both that copyright notice and this permission notice appear
46*38fd1498Szrj  * in supporting documentation.  Silicon Graphics makes no
47*38fd1498Szrj  * representations about the suitability of this software for any
48*38fd1498Szrj  * purpose.  It is provided "as is" without express or implied warranty.
49*38fd1498Szrj  */
50*38fd1498Szrj 
51*38fd1498Szrj /** @file bits/stl_algo.h
52*38fd1498Szrj  *  This is an internal header file, included by other library headers.
53*38fd1498Szrj  *  Do not attempt to use it directly. @headername{algorithm}
54*38fd1498Szrj  */
55*38fd1498Szrj 
56*38fd1498Szrj #ifndef _STL_ALGO_H
57*38fd1498Szrj #define _STL_ALGO_H 1
58*38fd1498Szrj 
59*38fd1498Szrj #include <cstdlib>	     // for rand
60*38fd1498Szrj #include <bits/algorithmfwd.h>
61*38fd1498Szrj #include <bits/stl_heap.h>
62*38fd1498Szrj #include <bits/stl_tempbuf.h>  // for _Temporary_buffer
63*38fd1498Szrj #include <bits/predefined_ops.h>
64*38fd1498Szrj 
65*38fd1498Szrj #if __cplusplus >= 201103L
66*38fd1498Szrj #include <bits/uniform_int_dist.h>
67*38fd1498Szrj #endif
68*38fd1498Szrj 
69*38fd1498Szrj // See concept_check.h for the __glibcxx_*_requires macros.
70*38fd1498Szrj 
_GLIBCXX_VISIBILITY(default)71*38fd1498Szrj namespace std _GLIBCXX_VISIBILITY(default)
72*38fd1498Szrj {
73*38fd1498Szrj _GLIBCXX_BEGIN_NAMESPACE_VERSION
74*38fd1498Szrj 
75*38fd1498Szrj   /// Swaps the median value of *__a, *__b and *__c under __comp to *__result
76*38fd1498Szrj   template<typename _Iterator, typename _Compare>
77*38fd1498Szrj     void
78*38fd1498Szrj     __move_median_to_first(_Iterator __result,_Iterator __a, _Iterator __b,
79*38fd1498Szrj 			   _Iterator __c, _Compare __comp)
80*38fd1498Szrj     {
81*38fd1498Szrj       if (__comp(__a, __b))
82*38fd1498Szrj 	{
83*38fd1498Szrj 	  if (__comp(__b, __c))
84*38fd1498Szrj 	    std::iter_swap(__result, __b);
85*38fd1498Szrj 	  else if (__comp(__a, __c))
86*38fd1498Szrj 	    std::iter_swap(__result, __c);
87*38fd1498Szrj 	  else
88*38fd1498Szrj 	    std::iter_swap(__result, __a);
89*38fd1498Szrj 	}
90*38fd1498Szrj       else if (__comp(__a, __c))
91*38fd1498Szrj 	std::iter_swap(__result, __a);
92*38fd1498Szrj       else if (__comp(__b, __c))
93*38fd1498Szrj 	std::iter_swap(__result, __c);
94*38fd1498Szrj       else
95*38fd1498Szrj 	std::iter_swap(__result, __b);
96*38fd1498Szrj     }
97*38fd1498Szrj 
98*38fd1498Szrj   /// This is an overload used by find algos for the Input Iterator case.
99*38fd1498Szrj   template<typename _InputIterator, typename _Predicate>
100*38fd1498Szrj     inline _InputIterator
101*38fd1498Szrj     __find_if(_InputIterator __first, _InputIterator __last,
102*38fd1498Szrj 	      _Predicate __pred, input_iterator_tag)
103*38fd1498Szrj     {
104*38fd1498Szrj       while (__first != __last && !__pred(__first))
105*38fd1498Szrj 	++__first;
106*38fd1498Szrj       return __first;
107*38fd1498Szrj     }
108*38fd1498Szrj 
109*38fd1498Szrj   /// This is an overload used by find algos for the RAI case.
110*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Predicate>
111*38fd1498Szrj     _RandomAccessIterator
112*38fd1498Szrj     __find_if(_RandomAccessIterator __first, _RandomAccessIterator __last,
113*38fd1498Szrj 	      _Predicate __pred, random_access_iterator_tag)
114*38fd1498Szrj     {
115*38fd1498Szrj       typename iterator_traits<_RandomAccessIterator>::difference_type
116*38fd1498Szrj 	__trip_count = (__last - __first) >> 2;
117*38fd1498Szrj 
118*38fd1498Szrj       for (; __trip_count > 0; --__trip_count)
119*38fd1498Szrj 	{
120*38fd1498Szrj 	  if (__pred(__first))
121*38fd1498Szrj 	    return __first;
122*38fd1498Szrj 	  ++__first;
123*38fd1498Szrj 
124*38fd1498Szrj 	  if (__pred(__first))
125*38fd1498Szrj 	    return __first;
126*38fd1498Szrj 	  ++__first;
127*38fd1498Szrj 
128*38fd1498Szrj 	  if (__pred(__first))
129*38fd1498Szrj 	    return __first;
130*38fd1498Szrj 	  ++__first;
131*38fd1498Szrj 
132*38fd1498Szrj 	  if (__pred(__first))
133*38fd1498Szrj 	    return __first;
134*38fd1498Szrj 	  ++__first;
135*38fd1498Szrj 	}
136*38fd1498Szrj 
137*38fd1498Szrj       switch (__last - __first)
138*38fd1498Szrj 	{
139*38fd1498Szrj 	case 3:
140*38fd1498Szrj 	  if (__pred(__first))
141*38fd1498Szrj 	    return __first;
142*38fd1498Szrj 	  ++__first;
143*38fd1498Szrj 	case 2:
144*38fd1498Szrj 	  if (__pred(__first))
145*38fd1498Szrj 	    return __first;
146*38fd1498Szrj 	  ++__first;
147*38fd1498Szrj 	case 1:
148*38fd1498Szrj 	  if (__pred(__first))
149*38fd1498Szrj 	    return __first;
150*38fd1498Szrj 	  ++__first;
151*38fd1498Szrj 	case 0:
152*38fd1498Szrj 	default:
153*38fd1498Szrj 	  return __last;
154*38fd1498Szrj 	}
155*38fd1498Szrj     }
156*38fd1498Szrj 
157*38fd1498Szrj   template<typename _Iterator, typename _Predicate>
158*38fd1498Szrj     inline _Iterator
159*38fd1498Szrj     __find_if(_Iterator __first, _Iterator __last, _Predicate __pred)
160*38fd1498Szrj     {
161*38fd1498Szrj       return __find_if(__first, __last, __pred,
162*38fd1498Szrj 		       std::__iterator_category(__first));
163*38fd1498Szrj     }
164*38fd1498Szrj 
165*38fd1498Szrj   /// Provided for stable_partition to use.
166*38fd1498Szrj   template<typename _InputIterator, typename _Predicate>
167*38fd1498Szrj     inline _InputIterator
168*38fd1498Szrj     __find_if_not(_InputIterator __first, _InputIterator __last,
169*38fd1498Szrj 		  _Predicate __pred)
170*38fd1498Szrj     {
171*38fd1498Szrj       return std::__find_if(__first, __last,
172*38fd1498Szrj 			    __gnu_cxx::__ops::__negate(__pred),
173*38fd1498Szrj 			    std::__iterator_category(__first));
174*38fd1498Szrj     }
175*38fd1498Szrj 
176*38fd1498Szrj   /// Like find_if_not(), but uses and updates a count of the
177*38fd1498Szrj   /// remaining range length instead of comparing against an end
178*38fd1498Szrj   /// iterator.
179*38fd1498Szrj   template<typename _InputIterator, typename _Predicate, typename _Distance>
180*38fd1498Szrj     _InputIterator
181*38fd1498Szrj     __find_if_not_n(_InputIterator __first, _Distance& __len, _Predicate __pred)
182*38fd1498Szrj     {
183*38fd1498Szrj       for (; __len; --__len,  (void) ++__first)
184*38fd1498Szrj 	if (!__pred(__first))
185*38fd1498Szrj 	  break;
186*38fd1498Szrj       return __first;
187*38fd1498Szrj     }
188*38fd1498Szrj 
189*38fd1498Szrj   // set_difference
190*38fd1498Szrj   // set_intersection
191*38fd1498Szrj   // set_symmetric_difference
192*38fd1498Szrj   // set_union
193*38fd1498Szrj   // for_each
194*38fd1498Szrj   // find
195*38fd1498Szrj   // find_if
196*38fd1498Szrj   // find_first_of
197*38fd1498Szrj   // adjacent_find
198*38fd1498Szrj   // count
199*38fd1498Szrj   // count_if
200*38fd1498Szrj   // search
201*38fd1498Szrj 
202*38fd1498Szrj   template<typename _ForwardIterator1, typename _ForwardIterator2,
203*38fd1498Szrj 	   typename _BinaryPredicate>
204*38fd1498Szrj     _ForwardIterator1
205*38fd1498Szrj     __search(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
206*38fd1498Szrj 	     _ForwardIterator2 __first2, _ForwardIterator2 __last2,
207*38fd1498Szrj 	     _BinaryPredicate  __predicate)
208*38fd1498Szrj     {
209*38fd1498Szrj       // Test for empty ranges
210*38fd1498Szrj       if (__first1 == __last1 || __first2 == __last2)
211*38fd1498Szrj 	return __first1;
212*38fd1498Szrj 
213*38fd1498Szrj       // Test for a pattern of length 1.
214*38fd1498Szrj       _ForwardIterator2 __p1(__first2);
215*38fd1498Szrj       if (++__p1 == __last2)
216*38fd1498Szrj 	return std::__find_if(__first1, __last1,
217*38fd1498Szrj 		__gnu_cxx::__ops::__iter_comp_iter(__predicate, __first2));
218*38fd1498Szrj 
219*38fd1498Szrj       // General case.
220*38fd1498Szrj       _ForwardIterator2 __p;
221*38fd1498Szrj       _ForwardIterator1 __current = __first1;
222*38fd1498Szrj 
223*38fd1498Szrj       for (;;)
224*38fd1498Szrj 	{
225*38fd1498Szrj 	  __first1 =
226*38fd1498Szrj 	    std::__find_if(__first1, __last1,
227*38fd1498Szrj 		__gnu_cxx::__ops::__iter_comp_iter(__predicate, __first2));
228*38fd1498Szrj 
229*38fd1498Szrj 	  if (__first1 == __last1)
230*38fd1498Szrj 	    return __last1;
231*38fd1498Szrj 
232*38fd1498Szrj 	  __p = __p1;
233*38fd1498Szrj 	  __current = __first1;
234*38fd1498Szrj 	  if (++__current == __last1)
235*38fd1498Szrj 	    return __last1;
236*38fd1498Szrj 
237*38fd1498Szrj 	  while (__predicate(__current, __p))
238*38fd1498Szrj 	    {
239*38fd1498Szrj 	      if (++__p == __last2)
240*38fd1498Szrj 		return __first1;
241*38fd1498Szrj 	      if (++__current == __last1)
242*38fd1498Szrj 		return __last1;
243*38fd1498Szrj 	    }
244*38fd1498Szrj 	  ++__first1;
245*38fd1498Szrj 	}
246*38fd1498Szrj       return __first1;
247*38fd1498Szrj     }
248*38fd1498Szrj 
249*38fd1498Szrj   // search_n
250*38fd1498Szrj 
251*38fd1498Szrj   /**
252*38fd1498Szrj    *  This is an helper function for search_n overloaded for forward iterators.
253*38fd1498Szrj   */
254*38fd1498Szrj   template<typename _ForwardIterator, typename _Integer,
255*38fd1498Szrj 	   typename _UnaryPredicate>
256*38fd1498Szrj     _ForwardIterator
257*38fd1498Szrj     __search_n_aux(_ForwardIterator __first, _ForwardIterator __last,
258*38fd1498Szrj 		   _Integer __count, _UnaryPredicate __unary_pred,
259*38fd1498Szrj 		   std::forward_iterator_tag)
260*38fd1498Szrj     {
261*38fd1498Szrj       __first = std::__find_if(__first, __last, __unary_pred);
262*38fd1498Szrj       while (__first != __last)
263*38fd1498Szrj 	{
264*38fd1498Szrj 	  typename iterator_traits<_ForwardIterator>::difference_type
265*38fd1498Szrj 	    __n = __count;
266*38fd1498Szrj 	  _ForwardIterator __i = __first;
267*38fd1498Szrj 	  ++__i;
268*38fd1498Szrj 	  while (__i != __last && __n != 1 && __unary_pred(__i))
269*38fd1498Szrj 	    {
270*38fd1498Szrj 	      ++__i;
271*38fd1498Szrj 	      --__n;
272*38fd1498Szrj 	    }
273*38fd1498Szrj 	  if (__n == 1)
274*38fd1498Szrj 	    return __first;
275*38fd1498Szrj 	  if (__i == __last)
276*38fd1498Szrj 	    return __last;
277*38fd1498Szrj 	  __first = std::__find_if(++__i, __last, __unary_pred);
278*38fd1498Szrj 	}
279*38fd1498Szrj       return __last;
280*38fd1498Szrj     }
281*38fd1498Szrj 
282*38fd1498Szrj   /**
283*38fd1498Szrj    *  This is an helper function for search_n overloaded for random access
284*38fd1498Szrj    *  iterators.
285*38fd1498Szrj   */
286*38fd1498Szrj   template<typename _RandomAccessIter, typename _Integer,
287*38fd1498Szrj 	   typename _UnaryPredicate>
288*38fd1498Szrj     _RandomAccessIter
289*38fd1498Szrj     __search_n_aux(_RandomAccessIter __first, _RandomAccessIter __last,
290*38fd1498Szrj 		   _Integer __count, _UnaryPredicate __unary_pred,
291*38fd1498Szrj 		   std::random_access_iterator_tag)
292*38fd1498Szrj     {
293*38fd1498Szrj       typedef typename std::iterator_traits<_RandomAccessIter>::difference_type
294*38fd1498Szrj 	_DistanceType;
295*38fd1498Szrj 
296*38fd1498Szrj       _DistanceType __tailSize = __last - __first;
297*38fd1498Szrj       _DistanceType __remainder = __count;
298*38fd1498Szrj 
299*38fd1498Szrj       while (__remainder <= __tailSize) // the main loop...
300*38fd1498Szrj 	{
301*38fd1498Szrj 	  __first += __remainder;
302*38fd1498Szrj 	  __tailSize -= __remainder;
303*38fd1498Szrj 	  // __first here is always pointing to one past the last element of
304*38fd1498Szrj 	  // next possible match.
305*38fd1498Szrj 	  _RandomAccessIter __backTrack = __first;
306*38fd1498Szrj 	  while (__unary_pred(--__backTrack))
307*38fd1498Szrj 	    {
308*38fd1498Szrj 	      if (--__remainder == 0)
309*38fd1498Szrj 		return (__first - __count); // Success
310*38fd1498Szrj 	    }
311*38fd1498Szrj 	  __remainder = __count + 1 - (__first - __backTrack);
312*38fd1498Szrj 	}
313*38fd1498Szrj       return __last; // Failure
314*38fd1498Szrj     }
315*38fd1498Szrj 
316*38fd1498Szrj   template<typename _ForwardIterator, typename _Integer,
317*38fd1498Szrj 	   typename _UnaryPredicate>
318*38fd1498Szrj     _ForwardIterator
319*38fd1498Szrj     __search_n(_ForwardIterator __first, _ForwardIterator __last,
320*38fd1498Szrj 	       _Integer __count,
321*38fd1498Szrj 	       _UnaryPredicate __unary_pred)
322*38fd1498Szrj     {
323*38fd1498Szrj       if (__count <= 0)
324*38fd1498Szrj 	return __first;
325*38fd1498Szrj 
326*38fd1498Szrj       if (__count == 1)
327*38fd1498Szrj 	return std::__find_if(__first, __last, __unary_pred);
328*38fd1498Szrj 
329*38fd1498Szrj       return std::__search_n_aux(__first, __last, __count, __unary_pred,
330*38fd1498Szrj 				 std::__iterator_category(__first));
331*38fd1498Szrj     }
332*38fd1498Szrj 
333*38fd1498Szrj   // find_end for forward iterators.
334*38fd1498Szrj   template<typename _ForwardIterator1, typename _ForwardIterator2,
335*38fd1498Szrj 	   typename _BinaryPredicate>
336*38fd1498Szrj     _ForwardIterator1
337*38fd1498Szrj     __find_end(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
338*38fd1498Szrj 	       _ForwardIterator2 __first2, _ForwardIterator2 __last2,
339*38fd1498Szrj 	       forward_iterator_tag, forward_iterator_tag,
340*38fd1498Szrj 	       _BinaryPredicate __comp)
341*38fd1498Szrj     {
342*38fd1498Szrj       if (__first2 == __last2)
343*38fd1498Szrj 	return __last1;
344*38fd1498Szrj 
345*38fd1498Szrj       _ForwardIterator1 __result = __last1;
346*38fd1498Szrj       while (1)
347*38fd1498Szrj 	{
348*38fd1498Szrj 	  _ForwardIterator1 __new_result
349*38fd1498Szrj 	    = std::__search(__first1, __last1, __first2, __last2, __comp);
350*38fd1498Szrj 	  if (__new_result == __last1)
351*38fd1498Szrj 	    return __result;
352*38fd1498Szrj 	  else
353*38fd1498Szrj 	    {
354*38fd1498Szrj 	      __result = __new_result;
355*38fd1498Szrj 	      __first1 = __new_result;
356*38fd1498Szrj 	      ++__first1;
357*38fd1498Szrj 	    }
358*38fd1498Szrj 	}
359*38fd1498Szrj     }
360*38fd1498Szrj 
361*38fd1498Szrj   // find_end for bidirectional iterators (much faster).
362*38fd1498Szrj   template<typename _BidirectionalIterator1, typename _BidirectionalIterator2,
363*38fd1498Szrj 	   typename _BinaryPredicate>
364*38fd1498Szrj     _BidirectionalIterator1
365*38fd1498Szrj     __find_end(_BidirectionalIterator1 __first1,
366*38fd1498Szrj 	       _BidirectionalIterator1 __last1,
367*38fd1498Szrj 	       _BidirectionalIterator2 __first2,
368*38fd1498Szrj 	       _BidirectionalIterator2 __last2,
369*38fd1498Szrj 	       bidirectional_iterator_tag, bidirectional_iterator_tag,
370*38fd1498Szrj 	       _BinaryPredicate __comp)
371*38fd1498Szrj     {
372*38fd1498Szrj       // concept requirements
373*38fd1498Szrj       __glibcxx_function_requires(_BidirectionalIteratorConcept<
374*38fd1498Szrj 				  _BidirectionalIterator1>)
375*38fd1498Szrj       __glibcxx_function_requires(_BidirectionalIteratorConcept<
376*38fd1498Szrj 				  _BidirectionalIterator2>)
377*38fd1498Szrj 
378*38fd1498Szrj       typedef reverse_iterator<_BidirectionalIterator1> _RevIterator1;
379*38fd1498Szrj       typedef reverse_iterator<_BidirectionalIterator2> _RevIterator2;
380*38fd1498Szrj 
381*38fd1498Szrj       _RevIterator1 __rlast1(__first1);
382*38fd1498Szrj       _RevIterator2 __rlast2(__first2);
383*38fd1498Szrj       _RevIterator1 __rresult = std::__search(_RevIterator1(__last1), __rlast1,
384*38fd1498Szrj 					      _RevIterator2(__last2), __rlast2,
385*38fd1498Szrj 					      __comp);
386*38fd1498Szrj 
387*38fd1498Szrj       if (__rresult == __rlast1)
388*38fd1498Szrj 	return __last1;
389*38fd1498Szrj       else
390*38fd1498Szrj 	{
391*38fd1498Szrj 	  _BidirectionalIterator1 __result = __rresult.base();
392*38fd1498Szrj 	  std::advance(__result, -std::distance(__first2, __last2));
393*38fd1498Szrj 	  return __result;
394*38fd1498Szrj 	}
395*38fd1498Szrj     }
396*38fd1498Szrj 
397*38fd1498Szrj   /**
398*38fd1498Szrj    *  @brief  Find last matching subsequence in a sequence.
399*38fd1498Szrj    *  @ingroup non_mutating_algorithms
400*38fd1498Szrj    *  @param  __first1  Start of range to search.
401*38fd1498Szrj    *  @param  __last1   End of range to search.
402*38fd1498Szrj    *  @param  __first2  Start of sequence to match.
403*38fd1498Szrj    *  @param  __last2   End of sequence to match.
404*38fd1498Szrj    *  @return   The last iterator @c i in the range
405*38fd1498Szrj    *  @p [__first1,__last1-(__last2-__first2)) such that @c *(i+N) ==
406*38fd1498Szrj    *  @p *(__first2+N) for each @c N in the range @p
407*38fd1498Szrj    *  [0,__last2-__first2), or @p __last1 if no such iterator exists.
408*38fd1498Szrj    *
409*38fd1498Szrj    *  Searches the range @p [__first1,__last1) for a sub-sequence that
410*38fd1498Szrj    *  compares equal value-by-value with the sequence given by @p
411*38fd1498Szrj    *  [__first2,__last2) and returns an iterator to the __first
412*38fd1498Szrj    *  element of the sub-sequence, or @p __last1 if the sub-sequence
413*38fd1498Szrj    *  is not found.  The sub-sequence will be the last such
414*38fd1498Szrj    *  subsequence contained in [__first1,__last1).
415*38fd1498Szrj    *
416*38fd1498Szrj    *  Because the sub-sequence must lie completely within the range @p
417*38fd1498Szrj    *  [__first1,__last1) it must start at a position less than @p
418*38fd1498Szrj    *  __last1-(__last2-__first2) where @p __last2-__first2 is the
419*38fd1498Szrj    *  length of the sub-sequence.  This means that the returned
420*38fd1498Szrj    *  iterator @c i will be in the range @p
421*38fd1498Szrj    *  [__first1,__last1-(__last2-__first2))
422*38fd1498Szrj   */
423*38fd1498Szrj   template<typename _ForwardIterator1, typename _ForwardIterator2>
424*38fd1498Szrj     inline _ForwardIterator1
425*38fd1498Szrj     find_end(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
426*38fd1498Szrj 	     _ForwardIterator2 __first2, _ForwardIterator2 __last2)
427*38fd1498Szrj     {
428*38fd1498Szrj       // concept requirements
429*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator1>)
430*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator2>)
431*38fd1498Szrj       __glibcxx_function_requires(_EqualOpConcept<
432*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator1>::value_type,
433*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator2>::value_type>)
434*38fd1498Szrj       __glibcxx_requires_valid_range(__first1, __last1);
435*38fd1498Szrj       __glibcxx_requires_valid_range(__first2, __last2);
436*38fd1498Szrj 
437*38fd1498Szrj       return std::__find_end(__first1, __last1, __first2, __last2,
438*38fd1498Szrj 			     std::__iterator_category(__first1),
439*38fd1498Szrj 			     std::__iterator_category(__first2),
440*38fd1498Szrj 			     __gnu_cxx::__ops::__iter_equal_to_iter());
441*38fd1498Szrj     }
442*38fd1498Szrj 
443*38fd1498Szrj   /**
444*38fd1498Szrj    *  @brief  Find last matching subsequence in a sequence using a predicate.
445*38fd1498Szrj    *  @ingroup non_mutating_algorithms
446*38fd1498Szrj    *  @param  __first1  Start of range to search.
447*38fd1498Szrj    *  @param  __last1   End of range to search.
448*38fd1498Szrj    *  @param  __first2  Start of sequence to match.
449*38fd1498Szrj    *  @param  __last2   End of sequence to match.
450*38fd1498Szrj    *  @param  __comp    The predicate to use.
451*38fd1498Szrj    *  @return The last iterator @c i in the range @p
452*38fd1498Szrj    *  [__first1,__last1-(__last2-__first2)) such that @c
453*38fd1498Szrj    *  predicate(*(i+N), @p (__first2+N)) is true for each @c N in the
454*38fd1498Szrj    *  range @p [0,__last2-__first2), or @p __last1 if no such iterator
455*38fd1498Szrj    *  exists.
456*38fd1498Szrj    *
457*38fd1498Szrj    *  Searches the range @p [__first1,__last1) for a sub-sequence that
458*38fd1498Szrj    *  compares equal value-by-value with the sequence given by @p
459*38fd1498Szrj    *  [__first2,__last2) using comp as a predicate and returns an
460*38fd1498Szrj    *  iterator to the first element of the sub-sequence, or @p __last1
461*38fd1498Szrj    *  if the sub-sequence is not found.  The sub-sequence will be the
462*38fd1498Szrj    *  last such subsequence contained in [__first,__last1).
463*38fd1498Szrj    *
464*38fd1498Szrj    *  Because the sub-sequence must lie completely within the range @p
465*38fd1498Szrj    *  [__first1,__last1) it must start at a position less than @p
466*38fd1498Szrj    *  __last1-(__last2-__first2) where @p __last2-__first2 is the
467*38fd1498Szrj    *  length of the sub-sequence.  This means that the returned
468*38fd1498Szrj    *  iterator @c i will be in the range @p
469*38fd1498Szrj    *  [__first1,__last1-(__last2-__first2))
470*38fd1498Szrj   */
471*38fd1498Szrj   template<typename _ForwardIterator1, typename _ForwardIterator2,
472*38fd1498Szrj 	   typename _BinaryPredicate>
473*38fd1498Szrj     inline _ForwardIterator1
474*38fd1498Szrj     find_end(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
475*38fd1498Szrj 	     _ForwardIterator2 __first2, _ForwardIterator2 __last2,
476*38fd1498Szrj 	     _BinaryPredicate __comp)
477*38fd1498Szrj     {
478*38fd1498Szrj       // concept requirements
479*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator1>)
480*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator2>)
481*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_BinaryPredicate,
482*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator1>::value_type,
483*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator2>::value_type>)
484*38fd1498Szrj       __glibcxx_requires_valid_range(__first1, __last1);
485*38fd1498Szrj       __glibcxx_requires_valid_range(__first2, __last2);
486*38fd1498Szrj 
487*38fd1498Szrj       return std::__find_end(__first1, __last1, __first2, __last2,
488*38fd1498Szrj 			     std::__iterator_category(__first1),
489*38fd1498Szrj 			     std::__iterator_category(__first2),
490*38fd1498Szrj 			     __gnu_cxx::__ops::__iter_comp_iter(__comp));
491*38fd1498Szrj     }
492*38fd1498Szrj 
493*38fd1498Szrj #if __cplusplus >= 201103L
494*38fd1498Szrj   /**
495*38fd1498Szrj    *  @brief  Checks that a predicate is true for all the elements
496*38fd1498Szrj    *          of a sequence.
497*38fd1498Szrj    *  @ingroup non_mutating_algorithms
498*38fd1498Szrj    *  @param  __first   An input iterator.
499*38fd1498Szrj    *  @param  __last    An input iterator.
500*38fd1498Szrj    *  @param  __pred    A predicate.
501*38fd1498Szrj    *  @return  True if the check is true, false otherwise.
502*38fd1498Szrj    *
503*38fd1498Szrj    *  Returns true if @p __pred is true for each element in the range
504*38fd1498Szrj    *  @p [__first,__last), and false otherwise.
505*38fd1498Szrj   */
506*38fd1498Szrj   template<typename _InputIterator, typename _Predicate>
507*38fd1498Szrj     inline bool
508*38fd1498Szrj     all_of(_InputIterator __first, _InputIterator __last, _Predicate __pred)
509*38fd1498Szrj     { return __last == std::find_if_not(__first, __last, __pred); }
510*38fd1498Szrj 
511*38fd1498Szrj   /**
512*38fd1498Szrj    *  @brief  Checks that a predicate is false for all the elements
513*38fd1498Szrj    *          of a sequence.
514*38fd1498Szrj    *  @ingroup non_mutating_algorithms
515*38fd1498Szrj    *  @param  __first   An input iterator.
516*38fd1498Szrj    *  @param  __last    An input iterator.
517*38fd1498Szrj    *  @param  __pred    A predicate.
518*38fd1498Szrj    *  @return  True if the check is true, false otherwise.
519*38fd1498Szrj    *
520*38fd1498Szrj    *  Returns true if @p __pred is false for each element in the range
521*38fd1498Szrj    *  @p [__first,__last), and false otherwise.
522*38fd1498Szrj   */
523*38fd1498Szrj   template<typename _InputIterator, typename _Predicate>
524*38fd1498Szrj     inline bool
525*38fd1498Szrj     none_of(_InputIterator __first, _InputIterator __last, _Predicate __pred)
526*38fd1498Szrj     { return __last == _GLIBCXX_STD_A::find_if(__first, __last, __pred); }
527*38fd1498Szrj 
528*38fd1498Szrj   /**
529*38fd1498Szrj    *  @brief  Checks that a predicate is false for at least an element
530*38fd1498Szrj    *          of a sequence.
531*38fd1498Szrj    *  @ingroup non_mutating_algorithms
532*38fd1498Szrj    *  @param  __first   An input iterator.
533*38fd1498Szrj    *  @param  __last    An input iterator.
534*38fd1498Szrj    *  @param  __pred    A predicate.
535*38fd1498Szrj    *  @return  True if the check is true, false otherwise.
536*38fd1498Szrj    *
537*38fd1498Szrj    *  Returns true if an element exists in the range @p
538*38fd1498Szrj    *  [__first,__last) such that @p __pred is true, and false
539*38fd1498Szrj    *  otherwise.
540*38fd1498Szrj   */
541*38fd1498Szrj   template<typename _InputIterator, typename _Predicate>
542*38fd1498Szrj     inline bool
543*38fd1498Szrj     any_of(_InputIterator __first, _InputIterator __last, _Predicate __pred)
544*38fd1498Szrj     { return !std::none_of(__first, __last, __pred); }
545*38fd1498Szrj 
546*38fd1498Szrj   /**
547*38fd1498Szrj    *  @brief  Find the first element in a sequence for which a
548*38fd1498Szrj    *          predicate is false.
549*38fd1498Szrj    *  @ingroup non_mutating_algorithms
550*38fd1498Szrj    *  @param  __first  An input iterator.
551*38fd1498Szrj    *  @param  __last   An input iterator.
552*38fd1498Szrj    *  @param  __pred   A predicate.
553*38fd1498Szrj    *  @return   The first iterator @c i in the range @p [__first,__last)
554*38fd1498Szrj    *  such that @p __pred(*i) is false, or @p __last if no such iterator exists.
555*38fd1498Szrj   */
556*38fd1498Szrj   template<typename _InputIterator, typename _Predicate>
557*38fd1498Szrj     inline _InputIterator
558*38fd1498Szrj     find_if_not(_InputIterator __first, _InputIterator __last,
559*38fd1498Szrj 		_Predicate __pred)
560*38fd1498Szrj     {
561*38fd1498Szrj       // concept requirements
562*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
563*38fd1498Szrj       __glibcxx_function_requires(_UnaryPredicateConcept<_Predicate,
564*38fd1498Szrj 	      typename iterator_traits<_InputIterator>::value_type>)
565*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
566*38fd1498Szrj       return std::__find_if_not(__first, __last,
567*38fd1498Szrj 				__gnu_cxx::__ops::__pred_iter(__pred));
568*38fd1498Szrj     }
569*38fd1498Szrj 
570*38fd1498Szrj   /**
571*38fd1498Szrj    *  @brief  Checks whether the sequence is partitioned.
572*38fd1498Szrj    *  @ingroup mutating_algorithms
573*38fd1498Szrj    *  @param  __first  An input iterator.
574*38fd1498Szrj    *  @param  __last   An input iterator.
575*38fd1498Szrj    *  @param  __pred   A predicate.
576*38fd1498Szrj    *  @return  True if the range @p [__first,__last) is partioned by @p __pred,
577*38fd1498Szrj    *  i.e. if all elements that satisfy @p __pred appear before those that
578*38fd1498Szrj    *  do not.
579*38fd1498Szrj   */
580*38fd1498Szrj   template<typename _InputIterator, typename _Predicate>
581*38fd1498Szrj     inline bool
582*38fd1498Szrj     is_partitioned(_InputIterator __first, _InputIterator __last,
583*38fd1498Szrj 		   _Predicate __pred)
584*38fd1498Szrj     {
585*38fd1498Szrj       __first = std::find_if_not(__first, __last, __pred);
586*38fd1498Szrj       if (__first == __last)
587*38fd1498Szrj 	return true;
588*38fd1498Szrj       ++__first;
589*38fd1498Szrj       return std::none_of(__first, __last, __pred);
590*38fd1498Szrj     }
591*38fd1498Szrj 
592*38fd1498Szrj   /**
593*38fd1498Szrj    *  @brief  Find the partition point of a partitioned range.
594*38fd1498Szrj    *  @ingroup mutating_algorithms
595*38fd1498Szrj    *  @param  __first   An iterator.
596*38fd1498Szrj    *  @param  __last    Another iterator.
597*38fd1498Szrj    *  @param  __pred    A predicate.
598*38fd1498Szrj    *  @return  An iterator @p mid such that @p all_of(__first, mid, __pred)
599*38fd1498Szrj    *           and @p none_of(mid, __last, __pred) are both true.
600*38fd1498Szrj   */
601*38fd1498Szrj   template<typename _ForwardIterator, typename _Predicate>
602*38fd1498Szrj     _ForwardIterator
603*38fd1498Szrj     partition_point(_ForwardIterator __first, _ForwardIterator __last,
604*38fd1498Szrj 		    _Predicate __pred)
605*38fd1498Szrj     {
606*38fd1498Szrj       // concept requirements
607*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
608*38fd1498Szrj       __glibcxx_function_requires(_UnaryPredicateConcept<_Predicate,
609*38fd1498Szrj 	      typename iterator_traits<_ForwardIterator>::value_type>)
610*38fd1498Szrj 
611*38fd1498Szrj       // A specific debug-mode test will be necessary...
612*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
613*38fd1498Szrj 
614*38fd1498Szrj       typedef typename iterator_traits<_ForwardIterator>::difference_type
615*38fd1498Szrj 	_DistanceType;
616*38fd1498Szrj 
617*38fd1498Szrj       _DistanceType __len = std::distance(__first, __last);
618*38fd1498Szrj       _DistanceType __half;
619*38fd1498Szrj       _ForwardIterator __middle;
620*38fd1498Szrj 
621*38fd1498Szrj       while (__len > 0)
622*38fd1498Szrj 	{
623*38fd1498Szrj 	  __half = __len >> 1;
624*38fd1498Szrj 	  __middle = __first;
625*38fd1498Szrj 	  std::advance(__middle, __half);
626*38fd1498Szrj 	  if (__pred(*__middle))
627*38fd1498Szrj 	    {
628*38fd1498Szrj 	      __first = __middle;
629*38fd1498Szrj 	      ++__first;
630*38fd1498Szrj 	      __len = __len - __half - 1;
631*38fd1498Szrj 	    }
632*38fd1498Szrj 	  else
633*38fd1498Szrj 	    __len = __half;
634*38fd1498Szrj 	}
635*38fd1498Szrj       return __first;
636*38fd1498Szrj     }
637*38fd1498Szrj #endif
638*38fd1498Szrj 
639*38fd1498Szrj   template<typename _InputIterator, typename _OutputIterator,
640*38fd1498Szrj 	   typename _Predicate>
641*38fd1498Szrj     _OutputIterator
642*38fd1498Szrj     __remove_copy_if(_InputIterator __first, _InputIterator __last,
643*38fd1498Szrj 		     _OutputIterator __result, _Predicate __pred)
644*38fd1498Szrj     {
645*38fd1498Szrj       for (; __first != __last; ++__first)
646*38fd1498Szrj 	if (!__pred(__first))
647*38fd1498Szrj 	  {
648*38fd1498Szrj 	    *__result = *__first;
649*38fd1498Szrj 	    ++__result;
650*38fd1498Szrj 	  }
651*38fd1498Szrj       return __result;
652*38fd1498Szrj     }
653*38fd1498Szrj 
654*38fd1498Szrj   /**
655*38fd1498Szrj    *  @brief Copy a sequence, removing elements of a given value.
656*38fd1498Szrj    *  @ingroup mutating_algorithms
657*38fd1498Szrj    *  @param  __first   An input iterator.
658*38fd1498Szrj    *  @param  __last    An input iterator.
659*38fd1498Szrj    *  @param  __result  An output iterator.
660*38fd1498Szrj    *  @param  __value   The value to be removed.
661*38fd1498Szrj    *  @return   An iterator designating the end of the resulting sequence.
662*38fd1498Szrj    *
663*38fd1498Szrj    *  Copies each element in the range @p [__first,__last) not equal
664*38fd1498Szrj    *  to @p __value to the range beginning at @p __result.
665*38fd1498Szrj    *  remove_copy() is stable, so the relative order of elements that
666*38fd1498Szrj    *  are copied is unchanged.
667*38fd1498Szrj   */
668*38fd1498Szrj   template<typename _InputIterator, typename _OutputIterator, typename _Tp>
669*38fd1498Szrj     inline _OutputIterator
670*38fd1498Szrj     remove_copy(_InputIterator __first, _InputIterator __last,
671*38fd1498Szrj 		_OutputIterator __result, const _Tp& __value)
672*38fd1498Szrj     {
673*38fd1498Szrj       // concept requirements
674*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
675*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
676*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
677*38fd1498Szrj       __glibcxx_function_requires(_EqualOpConcept<
678*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type, _Tp>)
679*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
680*38fd1498Szrj 
681*38fd1498Szrj       return std::__remove_copy_if(__first, __last, __result,
682*38fd1498Szrj 	__gnu_cxx::__ops::__iter_equals_val(__value));
683*38fd1498Szrj     }
684*38fd1498Szrj 
685*38fd1498Szrj   /**
686*38fd1498Szrj    *  @brief Copy a sequence, removing elements for which a predicate is true.
687*38fd1498Szrj    *  @ingroup mutating_algorithms
688*38fd1498Szrj    *  @param  __first   An input iterator.
689*38fd1498Szrj    *  @param  __last    An input iterator.
690*38fd1498Szrj    *  @param  __result  An output iterator.
691*38fd1498Szrj    *  @param  __pred    A predicate.
692*38fd1498Szrj    *  @return   An iterator designating the end of the resulting sequence.
693*38fd1498Szrj    *
694*38fd1498Szrj    *  Copies each element in the range @p [__first,__last) for which
695*38fd1498Szrj    *  @p __pred returns false to the range beginning at @p __result.
696*38fd1498Szrj    *
697*38fd1498Szrj    *  remove_copy_if() is stable, so the relative order of elements that are
698*38fd1498Szrj    *  copied is unchanged.
699*38fd1498Szrj   */
700*38fd1498Szrj   template<typename _InputIterator, typename _OutputIterator,
701*38fd1498Szrj 	   typename _Predicate>
702*38fd1498Szrj     inline _OutputIterator
703*38fd1498Szrj     remove_copy_if(_InputIterator __first, _InputIterator __last,
704*38fd1498Szrj 		   _OutputIterator __result, _Predicate __pred)
705*38fd1498Szrj     {
706*38fd1498Szrj       // concept requirements
707*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
708*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
709*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
710*38fd1498Szrj       __glibcxx_function_requires(_UnaryPredicateConcept<_Predicate,
711*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
712*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
713*38fd1498Szrj 
714*38fd1498Szrj       return std::__remove_copy_if(__first, __last, __result,
715*38fd1498Szrj 				   __gnu_cxx::__ops::__pred_iter(__pred));
716*38fd1498Szrj     }
717*38fd1498Szrj 
718*38fd1498Szrj #if __cplusplus >= 201103L
719*38fd1498Szrj   /**
720*38fd1498Szrj    *  @brief Copy the elements of a sequence for which a predicate is true.
721*38fd1498Szrj    *  @ingroup mutating_algorithms
722*38fd1498Szrj    *  @param  __first   An input iterator.
723*38fd1498Szrj    *  @param  __last    An input iterator.
724*38fd1498Szrj    *  @param  __result  An output iterator.
725*38fd1498Szrj    *  @param  __pred    A predicate.
726*38fd1498Szrj    *  @return   An iterator designating the end of the resulting sequence.
727*38fd1498Szrj    *
728*38fd1498Szrj    *  Copies each element in the range @p [__first,__last) for which
729*38fd1498Szrj    *  @p __pred returns true to the range beginning at @p __result.
730*38fd1498Szrj    *
731*38fd1498Szrj    *  copy_if() is stable, so the relative order of elements that are
732*38fd1498Szrj    *  copied is unchanged.
733*38fd1498Szrj   */
734*38fd1498Szrj   template<typename _InputIterator, typename _OutputIterator,
735*38fd1498Szrj 	   typename _Predicate>
736*38fd1498Szrj     _OutputIterator
737*38fd1498Szrj     copy_if(_InputIterator __first, _InputIterator __last,
738*38fd1498Szrj 	    _OutputIterator __result, _Predicate __pred)
739*38fd1498Szrj     {
740*38fd1498Szrj       // concept requirements
741*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
742*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
743*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
744*38fd1498Szrj       __glibcxx_function_requires(_UnaryPredicateConcept<_Predicate,
745*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
746*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
747*38fd1498Szrj 
748*38fd1498Szrj       for (; __first != __last; ++__first)
749*38fd1498Szrj 	if (__pred(*__first))
750*38fd1498Szrj 	  {
751*38fd1498Szrj 	    *__result = *__first;
752*38fd1498Szrj 	    ++__result;
753*38fd1498Szrj 	  }
754*38fd1498Szrj       return __result;
755*38fd1498Szrj     }
756*38fd1498Szrj 
757*38fd1498Szrj   template<typename _InputIterator, typename _Size, typename _OutputIterator>
758*38fd1498Szrj     _OutputIterator
759*38fd1498Szrj     __copy_n(_InputIterator __first, _Size __n,
760*38fd1498Szrj 	     _OutputIterator __result, input_iterator_tag)
761*38fd1498Szrj     {
762*38fd1498Szrj       if (__n > 0)
763*38fd1498Szrj 	{
764*38fd1498Szrj 	  while (true)
765*38fd1498Szrj 	    {
766*38fd1498Szrj 	      *__result = *__first;
767*38fd1498Szrj 	      ++__result;
768*38fd1498Szrj 	      if (--__n > 0)
769*38fd1498Szrj 		++__first;
770*38fd1498Szrj 	      else
771*38fd1498Szrj 		break;
772*38fd1498Szrj 	    }
773*38fd1498Szrj 	}
774*38fd1498Szrj       return __result;
775*38fd1498Szrj     }
776*38fd1498Szrj 
777*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Size,
778*38fd1498Szrj 	   typename _OutputIterator>
779*38fd1498Szrj     inline _OutputIterator
780*38fd1498Szrj     __copy_n(_RandomAccessIterator __first, _Size __n,
781*38fd1498Szrj 	     _OutputIterator __result, random_access_iterator_tag)
782*38fd1498Szrj     { return std::copy(__first, __first + __n, __result); }
783*38fd1498Szrj 
784*38fd1498Szrj   /**
785*38fd1498Szrj    *  @brief Copies the range [first,first+n) into [result,result+n).
786*38fd1498Szrj    *  @ingroup mutating_algorithms
787*38fd1498Szrj    *  @param  __first  An input iterator.
788*38fd1498Szrj    *  @param  __n      The number of elements to copy.
789*38fd1498Szrj    *  @param  __result An output iterator.
790*38fd1498Szrj    *  @return  result+n.
791*38fd1498Szrj    *
792*38fd1498Szrj    *  This inline function will boil down to a call to @c memmove whenever
793*38fd1498Szrj    *  possible.  Failing that, if random access iterators are passed, then the
794*38fd1498Szrj    *  loop count will be known (and therefore a candidate for compiler
795*38fd1498Szrj    *  optimizations such as unrolling).
796*38fd1498Szrj   */
797*38fd1498Szrj   template<typename _InputIterator, typename _Size, typename _OutputIterator>
798*38fd1498Szrj     inline _OutputIterator
799*38fd1498Szrj     copy_n(_InputIterator __first, _Size __n, _OutputIterator __result)
800*38fd1498Szrj     {
801*38fd1498Szrj       // concept requirements
802*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
803*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
804*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
805*38fd1498Szrj 
806*38fd1498Szrj       return std::__copy_n(__first, __n, __result,
807*38fd1498Szrj 			   std::__iterator_category(__first));
808*38fd1498Szrj     }
809*38fd1498Szrj 
810*38fd1498Szrj   /**
811*38fd1498Szrj    *  @brief Copy the elements of a sequence to separate output sequences
812*38fd1498Szrj    *         depending on the truth value of a predicate.
813*38fd1498Szrj    *  @ingroup mutating_algorithms
814*38fd1498Szrj    *  @param  __first   An input iterator.
815*38fd1498Szrj    *  @param  __last    An input iterator.
816*38fd1498Szrj    *  @param  __out_true   An output iterator.
817*38fd1498Szrj    *  @param  __out_false  An output iterator.
818*38fd1498Szrj    *  @param  __pred    A predicate.
819*38fd1498Szrj    *  @return   A pair designating the ends of the resulting sequences.
820*38fd1498Szrj    *
821*38fd1498Szrj    *  Copies each element in the range @p [__first,__last) for which
822*38fd1498Szrj    *  @p __pred returns true to the range beginning at @p out_true
823*38fd1498Szrj    *  and each element for which @p __pred returns false to @p __out_false.
824*38fd1498Szrj   */
825*38fd1498Szrj   template<typename _InputIterator, typename _OutputIterator1,
826*38fd1498Szrj 	   typename _OutputIterator2, typename _Predicate>
827*38fd1498Szrj     pair<_OutputIterator1, _OutputIterator2>
828*38fd1498Szrj     partition_copy(_InputIterator __first, _InputIterator __last,
829*38fd1498Szrj 		   _OutputIterator1 __out_true, _OutputIterator2 __out_false,
830*38fd1498Szrj 		   _Predicate __pred)
831*38fd1498Szrj     {
832*38fd1498Szrj       // concept requirements
833*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
834*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator1,
835*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
836*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator2,
837*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
838*38fd1498Szrj       __glibcxx_function_requires(_UnaryPredicateConcept<_Predicate,
839*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
840*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
841*38fd1498Szrj 
842*38fd1498Szrj       for (; __first != __last; ++__first)
843*38fd1498Szrj 	if (__pred(*__first))
844*38fd1498Szrj 	  {
845*38fd1498Szrj 	    *__out_true = *__first;
846*38fd1498Szrj 	    ++__out_true;
847*38fd1498Szrj 	  }
848*38fd1498Szrj 	else
849*38fd1498Szrj 	  {
850*38fd1498Szrj 	    *__out_false = *__first;
851*38fd1498Szrj 	    ++__out_false;
852*38fd1498Szrj 	  }
853*38fd1498Szrj 
854*38fd1498Szrj       return pair<_OutputIterator1, _OutputIterator2>(__out_true, __out_false);
855*38fd1498Szrj     }
856*38fd1498Szrj #endif
857*38fd1498Szrj 
858*38fd1498Szrj   template<typename _ForwardIterator, typename _Predicate>
859*38fd1498Szrj     _ForwardIterator
860*38fd1498Szrj     __remove_if(_ForwardIterator __first, _ForwardIterator __last,
861*38fd1498Szrj 		_Predicate __pred)
862*38fd1498Szrj     {
863*38fd1498Szrj       __first = std::__find_if(__first, __last, __pred);
864*38fd1498Szrj       if (__first == __last)
865*38fd1498Szrj 	return __first;
866*38fd1498Szrj       _ForwardIterator __result = __first;
867*38fd1498Szrj       ++__first;
868*38fd1498Szrj       for (; __first != __last; ++__first)
869*38fd1498Szrj 	if (!__pred(__first))
870*38fd1498Szrj 	  {
871*38fd1498Szrj 	    *__result = _GLIBCXX_MOVE(*__first);
872*38fd1498Szrj 	    ++__result;
873*38fd1498Szrj 	  }
874*38fd1498Szrj       return __result;
875*38fd1498Szrj     }
876*38fd1498Szrj 
877*38fd1498Szrj   /**
878*38fd1498Szrj    *  @brief Remove elements from a sequence.
879*38fd1498Szrj    *  @ingroup mutating_algorithms
880*38fd1498Szrj    *  @param  __first  An input iterator.
881*38fd1498Szrj    *  @param  __last   An input iterator.
882*38fd1498Szrj    *  @param  __value  The value to be removed.
883*38fd1498Szrj    *  @return   An iterator designating the end of the resulting sequence.
884*38fd1498Szrj    *
885*38fd1498Szrj    *  All elements equal to @p __value are removed from the range
886*38fd1498Szrj    *  @p [__first,__last).
887*38fd1498Szrj    *
888*38fd1498Szrj    *  remove() is stable, so the relative order of elements that are
889*38fd1498Szrj    *  not removed is unchanged.
890*38fd1498Szrj    *
891*38fd1498Szrj    *  Elements between the end of the resulting sequence and @p __last
892*38fd1498Szrj    *  are still present, but their value is unspecified.
893*38fd1498Szrj   */
894*38fd1498Szrj   template<typename _ForwardIterator, typename _Tp>
895*38fd1498Szrj     inline _ForwardIterator
896*38fd1498Szrj     remove(_ForwardIterator __first, _ForwardIterator __last,
897*38fd1498Szrj 	   const _Tp& __value)
898*38fd1498Szrj     {
899*38fd1498Szrj       // concept requirements
900*38fd1498Szrj       __glibcxx_function_requires(_Mutable_ForwardIteratorConcept<
901*38fd1498Szrj 				  _ForwardIterator>)
902*38fd1498Szrj       __glibcxx_function_requires(_EqualOpConcept<
903*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type, _Tp>)
904*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
905*38fd1498Szrj 
906*38fd1498Szrj       return std::__remove_if(__first, __last,
907*38fd1498Szrj 		__gnu_cxx::__ops::__iter_equals_val(__value));
908*38fd1498Szrj     }
909*38fd1498Szrj 
910*38fd1498Szrj   /**
911*38fd1498Szrj    *  @brief Remove elements from a sequence using a predicate.
912*38fd1498Szrj    *  @ingroup mutating_algorithms
913*38fd1498Szrj    *  @param  __first  A forward iterator.
914*38fd1498Szrj    *  @param  __last   A forward iterator.
915*38fd1498Szrj    *  @param  __pred   A predicate.
916*38fd1498Szrj    *  @return   An iterator designating the end of the resulting sequence.
917*38fd1498Szrj    *
918*38fd1498Szrj    *  All elements for which @p __pred returns true are removed from the range
919*38fd1498Szrj    *  @p [__first,__last).
920*38fd1498Szrj    *
921*38fd1498Szrj    *  remove_if() is stable, so the relative order of elements that are
922*38fd1498Szrj    *  not removed is unchanged.
923*38fd1498Szrj    *
924*38fd1498Szrj    *  Elements between the end of the resulting sequence and @p __last
925*38fd1498Szrj    *  are still present, but their value is unspecified.
926*38fd1498Szrj   */
927*38fd1498Szrj   template<typename _ForwardIterator, typename _Predicate>
928*38fd1498Szrj     inline _ForwardIterator
929*38fd1498Szrj     remove_if(_ForwardIterator __first, _ForwardIterator __last,
930*38fd1498Szrj 	      _Predicate __pred)
931*38fd1498Szrj     {
932*38fd1498Szrj       // concept requirements
933*38fd1498Szrj       __glibcxx_function_requires(_Mutable_ForwardIteratorConcept<
934*38fd1498Szrj 				  _ForwardIterator>)
935*38fd1498Szrj       __glibcxx_function_requires(_UnaryPredicateConcept<_Predicate,
936*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
937*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
938*38fd1498Szrj 
939*38fd1498Szrj       return std::__remove_if(__first, __last,
940*38fd1498Szrj 			      __gnu_cxx::__ops::__pred_iter(__pred));
941*38fd1498Szrj     }
942*38fd1498Szrj 
943*38fd1498Szrj   template<typename _ForwardIterator, typename _BinaryPredicate>
944*38fd1498Szrj     _ForwardIterator
945*38fd1498Szrj     __adjacent_find(_ForwardIterator __first, _ForwardIterator __last,
946*38fd1498Szrj 		    _BinaryPredicate __binary_pred)
947*38fd1498Szrj     {
948*38fd1498Szrj       if (__first == __last)
949*38fd1498Szrj 	return __last;
950*38fd1498Szrj       _ForwardIterator __next = __first;
951*38fd1498Szrj       while (++__next != __last)
952*38fd1498Szrj 	{
953*38fd1498Szrj 	  if (__binary_pred(__first, __next))
954*38fd1498Szrj 	    return __first;
955*38fd1498Szrj 	  __first = __next;
956*38fd1498Szrj 	}
957*38fd1498Szrj       return __last;
958*38fd1498Szrj     }
959*38fd1498Szrj 
960*38fd1498Szrj   template<typename _ForwardIterator, typename _BinaryPredicate>
961*38fd1498Szrj     _ForwardIterator
962*38fd1498Szrj     __unique(_ForwardIterator __first, _ForwardIterator __last,
963*38fd1498Szrj 	     _BinaryPredicate __binary_pred)
964*38fd1498Szrj     {
965*38fd1498Szrj       // Skip the beginning, if already unique.
966*38fd1498Szrj       __first = std::__adjacent_find(__first, __last, __binary_pred);
967*38fd1498Szrj       if (__first == __last)
968*38fd1498Szrj 	return __last;
969*38fd1498Szrj 
970*38fd1498Szrj       // Do the real copy work.
971*38fd1498Szrj       _ForwardIterator __dest = __first;
972*38fd1498Szrj       ++__first;
973*38fd1498Szrj       while (++__first != __last)
974*38fd1498Szrj 	if (!__binary_pred(__dest, __first))
975*38fd1498Szrj 	  *++__dest = _GLIBCXX_MOVE(*__first);
976*38fd1498Szrj       return ++__dest;
977*38fd1498Szrj     }
978*38fd1498Szrj 
979*38fd1498Szrj   /**
980*38fd1498Szrj    *  @brief Remove consecutive duplicate values from a sequence.
981*38fd1498Szrj    *  @ingroup mutating_algorithms
982*38fd1498Szrj    *  @param  __first  A forward iterator.
983*38fd1498Szrj    *  @param  __last   A forward iterator.
984*38fd1498Szrj    *  @return  An iterator designating the end of the resulting sequence.
985*38fd1498Szrj    *
986*38fd1498Szrj    *  Removes all but the first element from each group of consecutive
987*38fd1498Szrj    *  values that compare equal.
988*38fd1498Szrj    *  unique() is stable, so the relative order of elements that are
989*38fd1498Szrj    *  not removed is unchanged.
990*38fd1498Szrj    *  Elements between the end of the resulting sequence and @p __last
991*38fd1498Szrj    *  are still present, but their value is unspecified.
992*38fd1498Szrj   */
993*38fd1498Szrj   template<typename _ForwardIterator>
994*38fd1498Szrj     inline _ForwardIterator
995*38fd1498Szrj     unique(_ForwardIterator __first, _ForwardIterator __last)
996*38fd1498Szrj     {
997*38fd1498Szrj       // concept requirements
998*38fd1498Szrj       __glibcxx_function_requires(_Mutable_ForwardIteratorConcept<
999*38fd1498Szrj 				  _ForwardIterator>)
1000*38fd1498Szrj       __glibcxx_function_requires(_EqualityComparableConcept<
1001*38fd1498Szrj 		     typename iterator_traits<_ForwardIterator>::value_type>)
1002*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
1003*38fd1498Szrj 
1004*38fd1498Szrj       return std::__unique(__first, __last,
1005*38fd1498Szrj 			   __gnu_cxx::__ops::__iter_equal_to_iter());
1006*38fd1498Szrj     }
1007*38fd1498Szrj 
1008*38fd1498Szrj   /**
1009*38fd1498Szrj    *  @brief Remove consecutive values from a sequence using a predicate.
1010*38fd1498Szrj    *  @ingroup mutating_algorithms
1011*38fd1498Szrj    *  @param  __first        A forward iterator.
1012*38fd1498Szrj    *  @param  __last         A forward iterator.
1013*38fd1498Szrj    *  @param  __binary_pred  A binary predicate.
1014*38fd1498Szrj    *  @return  An iterator designating the end of the resulting sequence.
1015*38fd1498Szrj    *
1016*38fd1498Szrj    *  Removes all but the first element from each group of consecutive
1017*38fd1498Szrj    *  values for which @p __binary_pred returns true.
1018*38fd1498Szrj    *  unique() is stable, so the relative order of elements that are
1019*38fd1498Szrj    *  not removed is unchanged.
1020*38fd1498Szrj    *  Elements between the end of the resulting sequence and @p __last
1021*38fd1498Szrj    *  are still present, but their value is unspecified.
1022*38fd1498Szrj   */
1023*38fd1498Szrj   template<typename _ForwardIterator, typename _BinaryPredicate>
1024*38fd1498Szrj     inline _ForwardIterator
1025*38fd1498Szrj     unique(_ForwardIterator __first, _ForwardIterator __last,
1026*38fd1498Szrj 	   _BinaryPredicate __binary_pred)
1027*38fd1498Szrj     {
1028*38fd1498Szrj       // concept requirements
1029*38fd1498Szrj       __glibcxx_function_requires(_Mutable_ForwardIteratorConcept<
1030*38fd1498Szrj 				  _ForwardIterator>)
1031*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_BinaryPredicate,
1032*38fd1498Szrj 		typename iterator_traits<_ForwardIterator>::value_type,
1033*38fd1498Szrj 		typename iterator_traits<_ForwardIterator>::value_type>)
1034*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
1035*38fd1498Szrj 
1036*38fd1498Szrj       return std::__unique(__first, __last,
1037*38fd1498Szrj 			   __gnu_cxx::__ops::__iter_comp_iter(__binary_pred));
1038*38fd1498Szrj     }
1039*38fd1498Szrj 
1040*38fd1498Szrj   /**
1041*38fd1498Szrj    *  This is an uglified
1042*38fd1498Szrj    *  unique_copy(_InputIterator, _InputIterator, _OutputIterator,
1043*38fd1498Szrj    *              _BinaryPredicate)
1044*38fd1498Szrj    *  overloaded for forward iterators and output iterator as result.
1045*38fd1498Szrj   */
1046*38fd1498Szrj   template<typename _ForwardIterator, typename _OutputIterator,
1047*38fd1498Szrj 	   typename _BinaryPredicate>
1048*38fd1498Szrj     _OutputIterator
1049*38fd1498Szrj     __unique_copy(_ForwardIterator __first, _ForwardIterator __last,
1050*38fd1498Szrj 		  _OutputIterator __result, _BinaryPredicate __binary_pred,
1051*38fd1498Szrj 		  forward_iterator_tag, output_iterator_tag)
1052*38fd1498Szrj     {
1053*38fd1498Szrj       // concept requirements -- iterators already checked
1054*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_BinaryPredicate,
1055*38fd1498Szrj 	  typename iterator_traits<_ForwardIterator>::value_type,
1056*38fd1498Szrj 	  typename iterator_traits<_ForwardIterator>::value_type>)
1057*38fd1498Szrj 
1058*38fd1498Szrj       _ForwardIterator __next = __first;
1059*38fd1498Szrj       *__result = *__first;
1060*38fd1498Szrj       while (++__next != __last)
1061*38fd1498Szrj 	if (!__binary_pred(__first, __next))
1062*38fd1498Szrj 	  {
1063*38fd1498Szrj 	    __first = __next;
1064*38fd1498Szrj 	    *++__result = *__first;
1065*38fd1498Szrj 	  }
1066*38fd1498Szrj       return ++__result;
1067*38fd1498Szrj     }
1068*38fd1498Szrj 
1069*38fd1498Szrj   /**
1070*38fd1498Szrj    *  This is an uglified
1071*38fd1498Szrj    *  unique_copy(_InputIterator, _InputIterator, _OutputIterator,
1072*38fd1498Szrj    *              _BinaryPredicate)
1073*38fd1498Szrj    *  overloaded for input iterators and output iterator as result.
1074*38fd1498Szrj   */
1075*38fd1498Szrj   template<typename _InputIterator, typename _OutputIterator,
1076*38fd1498Szrj 	   typename _BinaryPredicate>
1077*38fd1498Szrj     _OutputIterator
1078*38fd1498Szrj     __unique_copy(_InputIterator __first, _InputIterator __last,
1079*38fd1498Szrj 		  _OutputIterator __result, _BinaryPredicate __binary_pred,
1080*38fd1498Szrj 		  input_iterator_tag, output_iterator_tag)
1081*38fd1498Szrj     {
1082*38fd1498Szrj       // concept requirements -- iterators already checked
1083*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_BinaryPredicate,
1084*38fd1498Szrj 	  typename iterator_traits<_InputIterator>::value_type,
1085*38fd1498Szrj 	  typename iterator_traits<_InputIterator>::value_type>)
1086*38fd1498Szrj 
1087*38fd1498Szrj       typename iterator_traits<_InputIterator>::value_type __value = *__first;
1088*38fd1498Szrj       __decltype(__gnu_cxx::__ops::__iter_comp_val(__binary_pred))
1089*38fd1498Szrj 	__rebound_pred
1090*38fd1498Szrj 	= __gnu_cxx::__ops::__iter_comp_val(__binary_pred);
1091*38fd1498Szrj       *__result = __value;
1092*38fd1498Szrj       while (++__first != __last)
1093*38fd1498Szrj 	if (!__rebound_pred(__first, __value))
1094*38fd1498Szrj 	  {
1095*38fd1498Szrj 	    __value = *__first;
1096*38fd1498Szrj 	    *++__result = __value;
1097*38fd1498Szrj 	  }
1098*38fd1498Szrj       return ++__result;
1099*38fd1498Szrj     }
1100*38fd1498Szrj 
1101*38fd1498Szrj   /**
1102*38fd1498Szrj    *  This is an uglified
1103*38fd1498Szrj    *  unique_copy(_InputIterator, _InputIterator, _OutputIterator,
1104*38fd1498Szrj    *              _BinaryPredicate)
1105*38fd1498Szrj    *  overloaded for input iterators and forward iterator as result.
1106*38fd1498Szrj   */
1107*38fd1498Szrj   template<typename _InputIterator, typename _ForwardIterator,
1108*38fd1498Szrj 	   typename _BinaryPredicate>
1109*38fd1498Szrj     _ForwardIterator
1110*38fd1498Szrj     __unique_copy(_InputIterator __first, _InputIterator __last,
1111*38fd1498Szrj 		  _ForwardIterator __result, _BinaryPredicate __binary_pred,
1112*38fd1498Szrj 		  input_iterator_tag, forward_iterator_tag)
1113*38fd1498Szrj     {
1114*38fd1498Szrj       // concept requirements -- iterators already checked
1115*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_BinaryPredicate,
1116*38fd1498Szrj 	  typename iterator_traits<_ForwardIterator>::value_type,
1117*38fd1498Szrj 	  typename iterator_traits<_InputIterator>::value_type>)
1118*38fd1498Szrj       *__result = *__first;
1119*38fd1498Szrj       while (++__first != __last)
1120*38fd1498Szrj 	if (!__binary_pred(__result, __first))
1121*38fd1498Szrj 	  *++__result = *__first;
1122*38fd1498Szrj       return ++__result;
1123*38fd1498Szrj     }
1124*38fd1498Szrj 
1125*38fd1498Szrj   /**
1126*38fd1498Szrj    *  This is an uglified reverse(_BidirectionalIterator,
1127*38fd1498Szrj    *                              _BidirectionalIterator)
1128*38fd1498Szrj    *  overloaded for bidirectional iterators.
1129*38fd1498Szrj   */
1130*38fd1498Szrj   template<typename _BidirectionalIterator>
1131*38fd1498Szrj     void
1132*38fd1498Szrj     __reverse(_BidirectionalIterator __first, _BidirectionalIterator __last,
1133*38fd1498Szrj 	      bidirectional_iterator_tag)
1134*38fd1498Szrj     {
1135*38fd1498Szrj       while (true)
1136*38fd1498Szrj 	if (__first == __last || __first == --__last)
1137*38fd1498Szrj 	  return;
1138*38fd1498Szrj 	else
1139*38fd1498Szrj 	  {
1140*38fd1498Szrj 	    std::iter_swap(__first, __last);
1141*38fd1498Szrj 	    ++__first;
1142*38fd1498Szrj 	  }
1143*38fd1498Szrj     }
1144*38fd1498Szrj 
1145*38fd1498Szrj   /**
1146*38fd1498Szrj    *  This is an uglified reverse(_BidirectionalIterator,
1147*38fd1498Szrj    *                              _BidirectionalIterator)
1148*38fd1498Szrj    *  overloaded for random access iterators.
1149*38fd1498Szrj   */
1150*38fd1498Szrj   template<typename _RandomAccessIterator>
1151*38fd1498Szrj     void
1152*38fd1498Szrj     __reverse(_RandomAccessIterator __first, _RandomAccessIterator __last,
1153*38fd1498Szrj 	      random_access_iterator_tag)
1154*38fd1498Szrj     {
1155*38fd1498Szrj       if (__first == __last)
1156*38fd1498Szrj 	return;
1157*38fd1498Szrj       --__last;
1158*38fd1498Szrj       while (__first < __last)
1159*38fd1498Szrj 	{
1160*38fd1498Szrj 	  std::iter_swap(__first, __last);
1161*38fd1498Szrj 	  ++__first;
1162*38fd1498Szrj 	  --__last;
1163*38fd1498Szrj 	}
1164*38fd1498Szrj     }
1165*38fd1498Szrj 
1166*38fd1498Szrj   /**
1167*38fd1498Szrj    *  @brief Reverse a sequence.
1168*38fd1498Szrj    *  @ingroup mutating_algorithms
1169*38fd1498Szrj    *  @param  __first  A bidirectional iterator.
1170*38fd1498Szrj    *  @param  __last   A bidirectional iterator.
1171*38fd1498Szrj    *  @return   reverse() returns no value.
1172*38fd1498Szrj    *
1173*38fd1498Szrj    *  Reverses the order of the elements in the range @p [__first,__last),
1174*38fd1498Szrj    *  so that the first element becomes the last etc.
1175*38fd1498Szrj    *  For every @c i such that @p 0<=i<=(__last-__first)/2), @p reverse()
1176*38fd1498Szrj    *  swaps @p *(__first+i) and @p *(__last-(i+1))
1177*38fd1498Szrj   */
1178*38fd1498Szrj   template<typename _BidirectionalIterator>
1179*38fd1498Szrj     inline void
1180*38fd1498Szrj     reverse(_BidirectionalIterator __first, _BidirectionalIterator __last)
1181*38fd1498Szrj     {
1182*38fd1498Szrj       // concept requirements
1183*38fd1498Szrj       __glibcxx_function_requires(_Mutable_BidirectionalIteratorConcept<
1184*38fd1498Szrj 				  _BidirectionalIterator>)
1185*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
1186*38fd1498Szrj       std::__reverse(__first, __last, std::__iterator_category(__first));
1187*38fd1498Szrj     }
1188*38fd1498Szrj 
1189*38fd1498Szrj   /**
1190*38fd1498Szrj    *  @brief Copy a sequence, reversing its elements.
1191*38fd1498Szrj    *  @ingroup mutating_algorithms
1192*38fd1498Szrj    *  @param  __first   A bidirectional iterator.
1193*38fd1498Szrj    *  @param  __last    A bidirectional iterator.
1194*38fd1498Szrj    *  @param  __result  An output iterator.
1195*38fd1498Szrj    *  @return  An iterator designating the end of the resulting sequence.
1196*38fd1498Szrj    *
1197*38fd1498Szrj    *  Copies the elements in the range @p [__first,__last) to the
1198*38fd1498Szrj    *  range @p [__result,__result+(__last-__first)) such that the
1199*38fd1498Szrj    *  order of the elements is reversed.  For every @c i such that @p
1200*38fd1498Szrj    *  0<=i<=(__last-__first), @p reverse_copy() performs the
1201*38fd1498Szrj    *  assignment @p *(__result+(__last-__first)-1-i) = *(__first+i).
1202*38fd1498Szrj    *  The ranges @p [__first,__last) and @p
1203*38fd1498Szrj    *  [__result,__result+(__last-__first)) must not overlap.
1204*38fd1498Szrj   */
1205*38fd1498Szrj   template<typename _BidirectionalIterator, typename _OutputIterator>
1206*38fd1498Szrj     _OutputIterator
1207*38fd1498Szrj     reverse_copy(_BidirectionalIterator __first, _BidirectionalIterator __last,
1208*38fd1498Szrj 		 _OutputIterator __result)
1209*38fd1498Szrj     {
1210*38fd1498Szrj       // concept requirements
1211*38fd1498Szrj       __glibcxx_function_requires(_BidirectionalIteratorConcept<
1212*38fd1498Szrj 				  _BidirectionalIterator>)
1213*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
1214*38fd1498Szrj 		typename iterator_traits<_BidirectionalIterator>::value_type>)
1215*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
1216*38fd1498Szrj 
1217*38fd1498Szrj       while (__first != __last)
1218*38fd1498Szrj 	{
1219*38fd1498Szrj 	  --__last;
1220*38fd1498Szrj 	  *__result = *__last;
1221*38fd1498Szrj 	  ++__result;
1222*38fd1498Szrj 	}
1223*38fd1498Szrj       return __result;
1224*38fd1498Szrj     }
1225*38fd1498Szrj 
1226*38fd1498Szrj   /**
1227*38fd1498Szrj    *  This is a helper function for the rotate algorithm specialized on RAIs.
1228*38fd1498Szrj    *  It returns the greatest common divisor of two integer values.
1229*38fd1498Szrj   */
1230*38fd1498Szrj   template<typename _EuclideanRingElement>
1231*38fd1498Szrj     _EuclideanRingElement
1232*38fd1498Szrj     __gcd(_EuclideanRingElement __m, _EuclideanRingElement __n)
1233*38fd1498Szrj     {
1234*38fd1498Szrj       while (__n != 0)
1235*38fd1498Szrj 	{
1236*38fd1498Szrj 	  _EuclideanRingElement __t = __m % __n;
1237*38fd1498Szrj 	  __m = __n;
1238*38fd1498Szrj 	  __n = __t;
1239*38fd1498Szrj 	}
1240*38fd1498Szrj       return __m;
1241*38fd1498Szrj     }
1242*38fd1498Szrj 
1243*38fd1498Szrj   inline namespace _V2
1244*38fd1498Szrj   {
1245*38fd1498Szrj 
1246*38fd1498Szrj   /// This is a helper function for the rotate algorithm.
1247*38fd1498Szrj   template<typename _ForwardIterator>
1248*38fd1498Szrj     _ForwardIterator
1249*38fd1498Szrj     __rotate(_ForwardIterator __first,
1250*38fd1498Szrj 	     _ForwardIterator __middle,
1251*38fd1498Szrj 	     _ForwardIterator __last,
1252*38fd1498Szrj 	     forward_iterator_tag)
1253*38fd1498Szrj     {
1254*38fd1498Szrj       if (__first == __middle)
1255*38fd1498Szrj 	return __last;
1256*38fd1498Szrj       else if (__last  == __middle)
1257*38fd1498Szrj 	return __first;
1258*38fd1498Szrj 
1259*38fd1498Szrj       _ForwardIterator __first2 = __middle;
1260*38fd1498Szrj       do
1261*38fd1498Szrj 	{
1262*38fd1498Szrj 	  std::iter_swap(__first, __first2);
1263*38fd1498Szrj 	  ++__first;
1264*38fd1498Szrj 	  ++__first2;
1265*38fd1498Szrj 	  if (__first == __middle)
1266*38fd1498Szrj 	    __middle = __first2;
1267*38fd1498Szrj 	}
1268*38fd1498Szrj       while (__first2 != __last);
1269*38fd1498Szrj 
1270*38fd1498Szrj       _ForwardIterator __ret = __first;
1271*38fd1498Szrj 
1272*38fd1498Szrj       __first2 = __middle;
1273*38fd1498Szrj 
1274*38fd1498Szrj       while (__first2 != __last)
1275*38fd1498Szrj 	{
1276*38fd1498Szrj 	  std::iter_swap(__first, __first2);
1277*38fd1498Szrj 	  ++__first;
1278*38fd1498Szrj 	  ++__first2;
1279*38fd1498Szrj 	  if (__first == __middle)
1280*38fd1498Szrj 	    __middle = __first2;
1281*38fd1498Szrj 	  else if (__first2 == __last)
1282*38fd1498Szrj 	    __first2 = __middle;
1283*38fd1498Szrj 	}
1284*38fd1498Szrj       return __ret;
1285*38fd1498Szrj     }
1286*38fd1498Szrj 
1287*38fd1498Szrj    /// This is a helper function for the rotate algorithm.
1288*38fd1498Szrj   template<typename _BidirectionalIterator>
1289*38fd1498Szrj     _BidirectionalIterator
1290*38fd1498Szrj     __rotate(_BidirectionalIterator __first,
1291*38fd1498Szrj 	     _BidirectionalIterator __middle,
1292*38fd1498Szrj 	     _BidirectionalIterator __last,
1293*38fd1498Szrj 	      bidirectional_iterator_tag)
1294*38fd1498Szrj     {
1295*38fd1498Szrj       // concept requirements
1296*38fd1498Szrj       __glibcxx_function_requires(_Mutable_BidirectionalIteratorConcept<
1297*38fd1498Szrj 				  _BidirectionalIterator>)
1298*38fd1498Szrj 
1299*38fd1498Szrj       if (__first == __middle)
1300*38fd1498Szrj 	return __last;
1301*38fd1498Szrj       else if (__last  == __middle)
1302*38fd1498Szrj 	return __first;
1303*38fd1498Szrj 
1304*38fd1498Szrj       std::__reverse(__first,  __middle, bidirectional_iterator_tag());
1305*38fd1498Szrj       std::__reverse(__middle, __last,   bidirectional_iterator_tag());
1306*38fd1498Szrj 
1307*38fd1498Szrj       while (__first != __middle && __middle != __last)
1308*38fd1498Szrj 	{
1309*38fd1498Szrj 	  std::iter_swap(__first, --__last);
1310*38fd1498Szrj 	  ++__first;
1311*38fd1498Szrj 	}
1312*38fd1498Szrj 
1313*38fd1498Szrj       if (__first == __middle)
1314*38fd1498Szrj 	{
1315*38fd1498Szrj 	  std::__reverse(__middle, __last,   bidirectional_iterator_tag());
1316*38fd1498Szrj 	  return __last;
1317*38fd1498Szrj 	}
1318*38fd1498Szrj       else
1319*38fd1498Szrj 	{
1320*38fd1498Szrj 	  std::__reverse(__first,  __middle, bidirectional_iterator_tag());
1321*38fd1498Szrj 	  return __first;
1322*38fd1498Szrj 	}
1323*38fd1498Szrj     }
1324*38fd1498Szrj 
1325*38fd1498Szrj   /// This is a helper function for the rotate algorithm.
1326*38fd1498Szrj   template<typename _RandomAccessIterator>
1327*38fd1498Szrj     _RandomAccessIterator
1328*38fd1498Szrj     __rotate(_RandomAccessIterator __first,
1329*38fd1498Szrj 	     _RandomAccessIterator __middle,
1330*38fd1498Szrj 	     _RandomAccessIterator __last,
1331*38fd1498Szrj 	     random_access_iterator_tag)
1332*38fd1498Szrj     {
1333*38fd1498Szrj       // concept requirements
1334*38fd1498Szrj       __glibcxx_function_requires(_Mutable_RandomAccessIteratorConcept<
1335*38fd1498Szrj 				  _RandomAccessIterator>)
1336*38fd1498Szrj 
1337*38fd1498Szrj       if (__first == __middle)
1338*38fd1498Szrj 	return __last;
1339*38fd1498Szrj       else if (__last  == __middle)
1340*38fd1498Szrj 	return __first;
1341*38fd1498Szrj 
1342*38fd1498Szrj       typedef typename iterator_traits<_RandomAccessIterator>::difference_type
1343*38fd1498Szrj 	_Distance;
1344*38fd1498Szrj       typedef typename iterator_traits<_RandomAccessIterator>::value_type
1345*38fd1498Szrj 	_ValueType;
1346*38fd1498Szrj 
1347*38fd1498Szrj       _Distance __n = __last   - __first;
1348*38fd1498Szrj       _Distance __k = __middle - __first;
1349*38fd1498Szrj 
1350*38fd1498Szrj       if (__k == __n - __k)
1351*38fd1498Szrj 	{
1352*38fd1498Szrj 	  std::swap_ranges(__first, __middle, __middle);
1353*38fd1498Szrj 	  return __middle;
1354*38fd1498Szrj 	}
1355*38fd1498Szrj 
1356*38fd1498Szrj       _RandomAccessIterator __p = __first;
1357*38fd1498Szrj       _RandomAccessIterator __ret = __first + (__last - __middle);
1358*38fd1498Szrj 
1359*38fd1498Szrj       for (;;)
1360*38fd1498Szrj 	{
1361*38fd1498Szrj 	  if (__k < __n - __k)
1362*38fd1498Szrj 	    {
1363*38fd1498Szrj 	      if (__is_pod(_ValueType) && __k == 1)
1364*38fd1498Szrj 		{
1365*38fd1498Szrj 		  _ValueType __t = _GLIBCXX_MOVE(*__p);
1366*38fd1498Szrj 		  _GLIBCXX_MOVE3(__p + 1, __p + __n, __p);
1367*38fd1498Szrj 		  *(__p + __n - 1) = _GLIBCXX_MOVE(__t);
1368*38fd1498Szrj 		  return __ret;
1369*38fd1498Szrj 		}
1370*38fd1498Szrj 	      _RandomAccessIterator __q = __p + __k;
1371*38fd1498Szrj 	      for (_Distance __i = 0; __i < __n - __k; ++ __i)
1372*38fd1498Szrj 		{
1373*38fd1498Szrj 		  std::iter_swap(__p, __q);
1374*38fd1498Szrj 		  ++__p;
1375*38fd1498Szrj 		  ++__q;
1376*38fd1498Szrj 		}
1377*38fd1498Szrj 	      __n %= __k;
1378*38fd1498Szrj 	      if (__n == 0)
1379*38fd1498Szrj 		return __ret;
1380*38fd1498Szrj 	      std::swap(__n, __k);
1381*38fd1498Szrj 	      __k = __n - __k;
1382*38fd1498Szrj 	    }
1383*38fd1498Szrj 	  else
1384*38fd1498Szrj 	    {
1385*38fd1498Szrj 	      __k = __n - __k;
1386*38fd1498Szrj 	      if (__is_pod(_ValueType) && __k == 1)
1387*38fd1498Szrj 		{
1388*38fd1498Szrj 		  _ValueType __t = _GLIBCXX_MOVE(*(__p + __n - 1));
1389*38fd1498Szrj 		  _GLIBCXX_MOVE_BACKWARD3(__p, __p + __n - 1, __p + __n);
1390*38fd1498Szrj 		  *__p = _GLIBCXX_MOVE(__t);
1391*38fd1498Szrj 		  return __ret;
1392*38fd1498Szrj 		}
1393*38fd1498Szrj 	      _RandomAccessIterator __q = __p + __n;
1394*38fd1498Szrj 	      __p = __q - __k;
1395*38fd1498Szrj 	      for (_Distance __i = 0; __i < __n - __k; ++ __i)
1396*38fd1498Szrj 		{
1397*38fd1498Szrj 		  --__p;
1398*38fd1498Szrj 		  --__q;
1399*38fd1498Szrj 		  std::iter_swap(__p, __q);
1400*38fd1498Szrj 		}
1401*38fd1498Szrj 	      __n %= __k;
1402*38fd1498Szrj 	      if (__n == 0)
1403*38fd1498Szrj 		return __ret;
1404*38fd1498Szrj 	      std::swap(__n, __k);
1405*38fd1498Szrj 	    }
1406*38fd1498Szrj 	}
1407*38fd1498Szrj     }
1408*38fd1498Szrj 
1409*38fd1498Szrj    // _GLIBCXX_RESOLVE_LIB_DEFECTS
1410*38fd1498Szrj    // DR 488. rotate throws away useful information
1411*38fd1498Szrj   /**
1412*38fd1498Szrj    *  @brief Rotate the elements of a sequence.
1413*38fd1498Szrj    *  @ingroup mutating_algorithms
1414*38fd1498Szrj    *  @param  __first   A forward iterator.
1415*38fd1498Szrj    *  @param  __middle  A forward iterator.
1416*38fd1498Szrj    *  @param  __last    A forward iterator.
1417*38fd1498Szrj    *  @return  first + (last - middle).
1418*38fd1498Szrj    *
1419*38fd1498Szrj    *  Rotates the elements of the range @p [__first,__last) by
1420*38fd1498Szrj    *  @p (__middle - __first) positions so that the element at @p __middle
1421*38fd1498Szrj    *  is moved to @p __first, the element at @p __middle+1 is moved to
1422*38fd1498Szrj    *  @p __first+1 and so on for each element in the range
1423*38fd1498Szrj    *  @p [__first,__last).
1424*38fd1498Szrj    *
1425*38fd1498Szrj    *  This effectively swaps the ranges @p [__first,__middle) and
1426*38fd1498Szrj    *  @p [__middle,__last).
1427*38fd1498Szrj    *
1428*38fd1498Szrj    *  Performs
1429*38fd1498Szrj    *   @p *(__first+(n+(__last-__middle))%(__last-__first))=*(__first+n)
1430*38fd1498Szrj    *  for each @p n in the range @p [0,__last-__first).
1431*38fd1498Szrj   */
1432*38fd1498Szrj   template<typename _ForwardIterator>
1433*38fd1498Szrj     inline _ForwardIterator
1434*38fd1498Szrj     rotate(_ForwardIterator __first, _ForwardIterator __middle,
1435*38fd1498Szrj 	   _ForwardIterator __last)
1436*38fd1498Szrj     {
1437*38fd1498Szrj       // concept requirements
1438*38fd1498Szrj       __glibcxx_function_requires(_Mutable_ForwardIteratorConcept<
1439*38fd1498Szrj 				  _ForwardIterator>)
1440*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __middle);
1441*38fd1498Szrj       __glibcxx_requires_valid_range(__middle, __last);
1442*38fd1498Szrj 
1443*38fd1498Szrj       return std::__rotate(__first, __middle, __last,
1444*38fd1498Szrj 			   std::__iterator_category(__first));
1445*38fd1498Szrj     }
1446*38fd1498Szrj 
1447*38fd1498Szrj   } // namespace _V2
1448*38fd1498Szrj 
1449*38fd1498Szrj   /**
1450*38fd1498Szrj    *  @brief Copy a sequence, rotating its elements.
1451*38fd1498Szrj    *  @ingroup mutating_algorithms
1452*38fd1498Szrj    *  @param  __first   A forward iterator.
1453*38fd1498Szrj    *  @param  __middle  A forward iterator.
1454*38fd1498Szrj    *  @param  __last    A forward iterator.
1455*38fd1498Szrj    *  @param  __result  An output iterator.
1456*38fd1498Szrj    *  @return   An iterator designating the end of the resulting sequence.
1457*38fd1498Szrj    *
1458*38fd1498Szrj    *  Copies the elements of the range @p [__first,__last) to the
1459*38fd1498Szrj    *  range beginning at @result, rotating the copied elements by
1460*38fd1498Szrj    *  @p (__middle-__first) positions so that the element at @p __middle
1461*38fd1498Szrj    *  is moved to @p __result, the element at @p __middle+1 is moved
1462*38fd1498Szrj    *  to @p __result+1 and so on for each element in the range @p
1463*38fd1498Szrj    *  [__first,__last).
1464*38fd1498Szrj    *
1465*38fd1498Szrj    *  Performs
1466*38fd1498Szrj    *  @p *(__result+(n+(__last-__middle))%(__last-__first))=*(__first+n)
1467*38fd1498Szrj    *  for each @p n in the range @p [0,__last-__first).
1468*38fd1498Szrj   */
1469*38fd1498Szrj   template<typename _ForwardIterator, typename _OutputIterator>
1470*38fd1498Szrj     inline _OutputIterator
1471*38fd1498Szrj     rotate_copy(_ForwardIterator __first, _ForwardIterator __middle,
1472*38fd1498Szrj 		_ForwardIterator __last, _OutputIterator __result)
1473*38fd1498Szrj     {
1474*38fd1498Szrj       // concept requirements
1475*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
1476*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
1477*38fd1498Szrj 		typename iterator_traits<_ForwardIterator>::value_type>)
1478*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __middle);
1479*38fd1498Szrj       __glibcxx_requires_valid_range(__middle, __last);
1480*38fd1498Szrj 
1481*38fd1498Szrj       return std::copy(__first, __middle,
1482*38fd1498Szrj 		       std::copy(__middle, __last, __result));
1483*38fd1498Szrj     }
1484*38fd1498Szrj 
1485*38fd1498Szrj   /// This is a helper function...
1486*38fd1498Szrj   template<typename _ForwardIterator, typename _Predicate>
1487*38fd1498Szrj     _ForwardIterator
1488*38fd1498Szrj     __partition(_ForwardIterator __first, _ForwardIterator __last,
1489*38fd1498Szrj 		_Predicate __pred, forward_iterator_tag)
1490*38fd1498Szrj     {
1491*38fd1498Szrj       if (__first == __last)
1492*38fd1498Szrj 	return __first;
1493*38fd1498Szrj 
1494*38fd1498Szrj       while (__pred(*__first))
1495*38fd1498Szrj 	if (++__first == __last)
1496*38fd1498Szrj 	  return __first;
1497*38fd1498Szrj 
1498*38fd1498Szrj       _ForwardIterator __next = __first;
1499*38fd1498Szrj 
1500*38fd1498Szrj       while (++__next != __last)
1501*38fd1498Szrj 	if (__pred(*__next))
1502*38fd1498Szrj 	  {
1503*38fd1498Szrj 	    std::iter_swap(__first, __next);
1504*38fd1498Szrj 	    ++__first;
1505*38fd1498Szrj 	  }
1506*38fd1498Szrj 
1507*38fd1498Szrj       return __first;
1508*38fd1498Szrj     }
1509*38fd1498Szrj 
1510*38fd1498Szrj   /// This is a helper function...
1511*38fd1498Szrj   template<typename _BidirectionalIterator, typename _Predicate>
1512*38fd1498Szrj     _BidirectionalIterator
1513*38fd1498Szrj     __partition(_BidirectionalIterator __first, _BidirectionalIterator __last,
1514*38fd1498Szrj 		_Predicate __pred, bidirectional_iterator_tag)
1515*38fd1498Szrj     {
1516*38fd1498Szrj       while (true)
1517*38fd1498Szrj 	{
1518*38fd1498Szrj 	  while (true)
1519*38fd1498Szrj 	    if (__first == __last)
1520*38fd1498Szrj 	      return __first;
1521*38fd1498Szrj 	    else if (__pred(*__first))
1522*38fd1498Szrj 	      ++__first;
1523*38fd1498Szrj 	    else
1524*38fd1498Szrj 	      break;
1525*38fd1498Szrj 	  --__last;
1526*38fd1498Szrj 	  while (true)
1527*38fd1498Szrj 	    if (__first == __last)
1528*38fd1498Szrj 	      return __first;
1529*38fd1498Szrj 	    else if (!bool(__pred(*__last)))
1530*38fd1498Szrj 	      --__last;
1531*38fd1498Szrj 	    else
1532*38fd1498Szrj 	      break;
1533*38fd1498Szrj 	  std::iter_swap(__first, __last);
1534*38fd1498Szrj 	  ++__first;
1535*38fd1498Szrj 	}
1536*38fd1498Szrj     }
1537*38fd1498Szrj 
1538*38fd1498Szrj   // partition
1539*38fd1498Szrj 
1540*38fd1498Szrj   /// This is a helper function...
1541*38fd1498Szrj   /// Requires __first != __last and !__pred(__first)
1542*38fd1498Szrj   /// and __len == distance(__first, __last).
1543*38fd1498Szrj   ///
1544*38fd1498Szrj   /// !__pred(__first) allows us to guarantee that we don't
1545*38fd1498Szrj   /// move-assign an element onto itself.
1546*38fd1498Szrj   template<typename _ForwardIterator, typename _Pointer, typename _Predicate,
1547*38fd1498Szrj 	   typename _Distance>
1548*38fd1498Szrj     _ForwardIterator
1549*38fd1498Szrj     __stable_partition_adaptive(_ForwardIterator __first,
1550*38fd1498Szrj 				_ForwardIterator __last,
1551*38fd1498Szrj 				_Predicate __pred, _Distance __len,
1552*38fd1498Szrj 				_Pointer __buffer,
1553*38fd1498Szrj 				_Distance __buffer_size)
1554*38fd1498Szrj     {
1555*38fd1498Szrj       if (__len == 1)
1556*38fd1498Szrj 	return __first;
1557*38fd1498Szrj 
1558*38fd1498Szrj       if (__len <= __buffer_size)
1559*38fd1498Szrj 	{
1560*38fd1498Szrj 	  _ForwardIterator __result1 = __first;
1561*38fd1498Szrj 	  _Pointer __result2 = __buffer;
1562*38fd1498Szrj 
1563*38fd1498Szrj 	  // The precondition guarantees that !__pred(__first), so
1564*38fd1498Szrj 	  // move that element to the buffer before starting the loop.
1565*38fd1498Szrj 	  // This ensures that we only call __pred once per element.
1566*38fd1498Szrj 	  *__result2 = _GLIBCXX_MOVE(*__first);
1567*38fd1498Szrj 	  ++__result2;
1568*38fd1498Szrj 	  ++__first;
1569*38fd1498Szrj 	  for (; __first != __last; ++__first)
1570*38fd1498Szrj 	    if (__pred(__first))
1571*38fd1498Szrj 	      {
1572*38fd1498Szrj 		*__result1 = _GLIBCXX_MOVE(*__first);
1573*38fd1498Szrj 		++__result1;
1574*38fd1498Szrj 	      }
1575*38fd1498Szrj 	    else
1576*38fd1498Szrj 	      {
1577*38fd1498Szrj 		*__result2 = _GLIBCXX_MOVE(*__first);
1578*38fd1498Szrj 		++__result2;
1579*38fd1498Szrj 	      }
1580*38fd1498Szrj 
1581*38fd1498Szrj 	  _GLIBCXX_MOVE3(__buffer, __result2, __result1);
1582*38fd1498Szrj 	  return __result1;
1583*38fd1498Szrj 	}
1584*38fd1498Szrj 
1585*38fd1498Szrj       _ForwardIterator __middle = __first;
1586*38fd1498Szrj       std::advance(__middle, __len / 2);
1587*38fd1498Szrj       _ForwardIterator __left_split =
1588*38fd1498Szrj 	std::__stable_partition_adaptive(__first, __middle, __pred,
1589*38fd1498Szrj 					 __len / 2, __buffer,
1590*38fd1498Szrj 					 __buffer_size);
1591*38fd1498Szrj 
1592*38fd1498Szrj       // Advance past true-predicate values to satisfy this
1593*38fd1498Szrj       // function's preconditions.
1594*38fd1498Szrj       _Distance __right_len = __len - __len / 2;
1595*38fd1498Szrj       _ForwardIterator __right_split =
1596*38fd1498Szrj 	std::__find_if_not_n(__middle, __right_len, __pred);
1597*38fd1498Szrj 
1598*38fd1498Szrj       if (__right_len)
1599*38fd1498Szrj 	__right_split =
1600*38fd1498Szrj 	  std::__stable_partition_adaptive(__right_split, __last, __pred,
1601*38fd1498Szrj 					   __right_len,
1602*38fd1498Szrj 					   __buffer, __buffer_size);
1603*38fd1498Szrj 
1604*38fd1498Szrj       std::rotate(__left_split, __middle, __right_split);
1605*38fd1498Szrj       std::advance(__left_split, std::distance(__middle, __right_split));
1606*38fd1498Szrj       return __left_split;
1607*38fd1498Szrj     }
1608*38fd1498Szrj 
1609*38fd1498Szrj   template<typename _ForwardIterator, typename _Predicate>
1610*38fd1498Szrj     _ForwardIterator
1611*38fd1498Szrj     __stable_partition(_ForwardIterator __first, _ForwardIterator __last,
1612*38fd1498Szrj 		       _Predicate __pred)
1613*38fd1498Szrj     {
1614*38fd1498Szrj       __first = std::__find_if_not(__first, __last, __pred);
1615*38fd1498Szrj 
1616*38fd1498Szrj       if (__first == __last)
1617*38fd1498Szrj 	return __first;
1618*38fd1498Szrj 
1619*38fd1498Szrj       typedef typename iterator_traits<_ForwardIterator>::value_type
1620*38fd1498Szrj 	_ValueType;
1621*38fd1498Szrj       typedef typename iterator_traits<_ForwardIterator>::difference_type
1622*38fd1498Szrj 	_DistanceType;
1623*38fd1498Szrj 
1624*38fd1498Szrj       _Temporary_buffer<_ForwardIterator, _ValueType> __buf(__first, __last);
1625*38fd1498Szrj       return
1626*38fd1498Szrj 	std::__stable_partition_adaptive(__first, __last, __pred,
1627*38fd1498Szrj 					 _DistanceType(__buf.requested_size()),
1628*38fd1498Szrj 					 __buf.begin(),
1629*38fd1498Szrj 					 _DistanceType(__buf.size()));
1630*38fd1498Szrj     }
1631*38fd1498Szrj 
1632*38fd1498Szrj   /**
1633*38fd1498Szrj    *  @brief Move elements for which a predicate is true to the beginning
1634*38fd1498Szrj    *         of a sequence, preserving relative ordering.
1635*38fd1498Szrj    *  @ingroup mutating_algorithms
1636*38fd1498Szrj    *  @param  __first   A forward iterator.
1637*38fd1498Szrj    *  @param  __last    A forward iterator.
1638*38fd1498Szrj    *  @param  __pred    A predicate functor.
1639*38fd1498Szrj    *  @return  An iterator @p middle such that @p __pred(i) is true for each
1640*38fd1498Szrj    *  iterator @p i in the range @p [first,middle) and false for each @p i
1641*38fd1498Szrj    *  in the range @p [middle,last).
1642*38fd1498Szrj    *
1643*38fd1498Szrj    *  Performs the same function as @p partition() with the additional
1644*38fd1498Szrj    *  guarantee that the relative ordering of elements in each group is
1645*38fd1498Szrj    *  preserved, so any two elements @p x and @p y in the range
1646*38fd1498Szrj    *  @p [__first,__last) such that @p __pred(x)==__pred(y) will have the same
1647*38fd1498Szrj    *  relative ordering after calling @p stable_partition().
1648*38fd1498Szrj   */
1649*38fd1498Szrj   template<typename _ForwardIterator, typename _Predicate>
1650*38fd1498Szrj     inline _ForwardIterator
1651*38fd1498Szrj     stable_partition(_ForwardIterator __first, _ForwardIterator __last,
1652*38fd1498Szrj 		     _Predicate __pred)
1653*38fd1498Szrj     {
1654*38fd1498Szrj       // concept requirements
1655*38fd1498Szrj       __glibcxx_function_requires(_Mutable_ForwardIteratorConcept<
1656*38fd1498Szrj 				  _ForwardIterator>)
1657*38fd1498Szrj       __glibcxx_function_requires(_UnaryPredicateConcept<_Predicate,
1658*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
1659*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
1660*38fd1498Szrj 
1661*38fd1498Szrj       return std::__stable_partition(__first, __last,
1662*38fd1498Szrj 				     __gnu_cxx::__ops::__pred_iter(__pred));
1663*38fd1498Szrj     }
1664*38fd1498Szrj 
1665*38fd1498Szrj   /// This is a helper function for the sort routines.
1666*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
1667*38fd1498Szrj     void
1668*38fd1498Szrj     __heap_select(_RandomAccessIterator __first,
1669*38fd1498Szrj 		  _RandomAccessIterator __middle,
1670*38fd1498Szrj 		  _RandomAccessIterator __last, _Compare __comp)
1671*38fd1498Szrj     {
1672*38fd1498Szrj       std::__make_heap(__first, __middle, __comp);
1673*38fd1498Szrj       for (_RandomAccessIterator __i = __middle; __i < __last; ++__i)
1674*38fd1498Szrj 	if (__comp(__i, __first))
1675*38fd1498Szrj 	  std::__pop_heap(__first, __middle, __i, __comp);
1676*38fd1498Szrj     }
1677*38fd1498Szrj 
1678*38fd1498Szrj   // partial_sort
1679*38fd1498Szrj 
1680*38fd1498Szrj   template<typename _InputIterator, typename _RandomAccessIterator,
1681*38fd1498Szrj 	   typename _Compare>
1682*38fd1498Szrj     _RandomAccessIterator
1683*38fd1498Szrj     __partial_sort_copy(_InputIterator __first, _InputIterator __last,
1684*38fd1498Szrj 			_RandomAccessIterator __result_first,
1685*38fd1498Szrj 			_RandomAccessIterator __result_last,
1686*38fd1498Szrj 			_Compare __comp)
1687*38fd1498Szrj     {
1688*38fd1498Szrj       typedef typename iterator_traits<_InputIterator>::value_type
1689*38fd1498Szrj 	_InputValueType;
1690*38fd1498Szrj       typedef iterator_traits<_RandomAccessIterator> _RItTraits;
1691*38fd1498Szrj       typedef typename _RItTraits::difference_type _DistanceType;
1692*38fd1498Szrj 
1693*38fd1498Szrj       if (__result_first == __result_last)
1694*38fd1498Szrj 	return __result_last;
1695*38fd1498Szrj       _RandomAccessIterator __result_real_last = __result_first;
1696*38fd1498Szrj       while (__first != __last && __result_real_last != __result_last)
1697*38fd1498Szrj 	{
1698*38fd1498Szrj 	  *__result_real_last = *__first;
1699*38fd1498Szrj 	  ++__result_real_last;
1700*38fd1498Szrj 	  ++__first;
1701*38fd1498Szrj 	}
1702*38fd1498Szrj 
1703*38fd1498Szrj       std::__make_heap(__result_first, __result_real_last, __comp);
1704*38fd1498Szrj       while (__first != __last)
1705*38fd1498Szrj 	{
1706*38fd1498Szrj 	  if (__comp(__first, __result_first))
1707*38fd1498Szrj 	    std::__adjust_heap(__result_first, _DistanceType(0),
1708*38fd1498Szrj 			       _DistanceType(__result_real_last
1709*38fd1498Szrj 					     - __result_first),
1710*38fd1498Szrj 			       _InputValueType(*__first), __comp);
1711*38fd1498Szrj 	  ++__first;
1712*38fd1498Szrj 	}
1713*38fd1498Szrj       std::__sort_heap(__result_first, __result_real_last, __comp);
1714*38fd1498Szrj       return __result_real_last;
1715*38fd1498Szrj     }
1716*38fd1498Szrj 
1717*38fd1498Szrj   /**
1718*38fd1498Szrj    *  @brief Copy the smallest elements of a sequence.
1719*38fd1498Szrj    *  @ingroup sorting_algorithms
1720*38fd1498Szrj    *  @param  __first   An iterator.
1721*38fd1498Szrj    *  @param  __last    Another iterator.
1722*38fd1498Szrj    *  @param  __result_first   A random-access iterator.
1723*38fd1498Szrj    *  @param  __result_last    Another random-access iterator.
1724*38fd1498Szrj    *  @return   An iterator indicating the end of the resulting sequence.
1725*38fd1498Szrj    *
1726*38fd1498Szrj    *  Copies and sorts the smallest N values from the range @p [__first,__last)
1727*38fd1498Szrj    *  to the range beginning at @p __result_first, where the number of
1728*38fd1498Szrj    *  elements to be copied, @p N, is the smaller of @p (__last-__first) and
1729*38fd1498Szrj    *  @p (__result_last-__result_first).
1730*38fd1498Szrj    *  After the sort if @e i and @e j are iterators in the range
1731*38fd1498Szrj    *  @p [__result_first,__result_first+N) such that i precedes j then
1732*38fd1498Szrj    *  *j<*i is false.
1733*38fd1498Szrj    *  The value returned is @p __result_first+N.
1734*38fd1498Szrj   */
1735*38fd1498Szrj   template<typename _InputIterator, typename _RandomAccessIterator>
1736*38fd1498Szrj     inline _RandomAccessIterator
1737*38fd1498Szrj     partial_sort_copy(_InputIterator __first, _InputIterator __last,
1738*38fd1498Szrj 		      _RandomAccessIterator __result_first,
1739*38fd1498Szrj 		      _RandomAccessIterator __result_last)
1740*38fd1498Szrj     {
1741*38fd1498Szrj #ifdef _GLIBCXX_CONCEPT_CHECKS
1742*38fd1498Szrj       typedef typename iterator_traits<_InputIterator>::value_type
1743*38fd1498Szrj 	_InputValueType;
1744*38fd1498Szrj       typedef typename iterator_traits<_RandomAccessIterator>::value_type
1745*38fd1498Szrj 	_OutputValueType;
1746*38fd1498Szrj #endif
1747*38fd1498Szrj 
1748*38fd1498Szrj       // concept requirements
1749*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
1750*38fd1498Szrj       __glibcxx_function_requires(_ConvertibleConcept<_InputValueType,
1751*38fd1498Szrj 				  _OutputValueType>)
1752*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<_InputValueType,
1753*38fd1498Szrj 						     _OutputValueType>)
1754*38fd1498Szrj       __glibcxx_function_requires(_LessThanComparableConcept<_OutputValueType>)
1755*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
1756*38fd1498Szrj       __glibcxx_requires_irreflexive(__first, __last);
1757*38fd1498Szrj       __glibcxx_requires_valid_range(__result_first, __result_last);
1758*38fd1498Szrj 
1759*38fd1498Szrj       return std::__partial_sort_copy(__first, __last,
1760*38fd1498Szrj 				      __result_first, __result_last,
1761*38fd1498Szrj 				      __gnu_cxx::__ops::__iter_less_iter());
1762*38fd1498Szrj     }
1763*38fd1498Szrj 
1764*38fd1498Szrj   /**
1765*38fd1498Szrj    *  @brief Copy the smallest elements of a sequence using a predicate for
1766*38fd1498Szrj    *         comparison.
1767*38fd1498Szrj    *  @ingroup sorting_algorithms
1768*38fd1498Szrj    *  @param  __first   An input iterator.
1769*38fd1498Szrj    *  @param  __last    Another input iterator.
1770*38fd1498Szrj    *  @param  __result_first   A random-access iterator.
1771*38fd1498Szrj    *  @param  __result_last    Another random-access iterator.
1772*38fd1498Szrj    *  @param  __comp    A comparison functor.
1773*38fd1498Szrj    *  @return   An iterator indicating the end of the resulting sequence.
1774*38fd1498Szrj    *
1775*38fd1498Szrj    *  Copies and sorts the smallest N values from the range @p [__first,__last)
1776*38fd1498Szrj    *  to the range beginning at @p result_first, where the number of
1777*38fd1498Szrj    *  elements to be copied, @p N, is the smaller of @p (__last-__first) and
1778*38fd1498Szrj    *  @p (__result_last-__result_first).
1779*38fd1498Szrj    *  After the sort if @e i and @e j are iterators in the range
1780*38fd1498Szrj    *  @p [__result_first,__result_first+N) such that i precedes j then
1781*38fd1498Szrj    *  @p __comp(*j,*i) is false.
1782*38fd1498Szrj    *  The value returned is @p __result_first+N.
1783*38fd1498Szrj   */
1784*38fd1498Szrj   template<typename _InputIterator, typename _RandomAccessIterator,
1785*38fd1498Szrj 	   typename _Compare>
1786*38fd1498Szrj     inline _RandomAccessIterator
1787*38fd1498Szrj     partial_sort_copy(_InputIterator __first, _InputIterator __last,
1788*38fd1498Szrj 		      _RandomAccessIterator __result_first,
1789*38fd1498Szrj 		      _RandomAccessIterator __result_last,
1790*38fd1498Szrj 		      _Compare __comp)
1791*38fd1498Szrj     {
1792*38fd1498Szrj #ifdef _GLIBCXX_CONCEPT_CHECKS
1793*38fd1498Szrj       typedef typename iterator_traits<_InputIterator>::value_type
1794*38fd1498Szrj 	_InputValueType;
1795*38fd1498Szrj       typedef typename iterator_traits<_RandomAccessIterator>::value_type
1796*38fd1498Szrj 	_OutputValueType;
1797*38fd1498Szrj #endif
1798*38fd1498Szrj 
1799*38fd1498Szrj       // concept requirements
1800*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
1801*38fd1498Szrj       __glibcxx_function_requires(_Mutable_RandomAccessIteratorConcept<
1802*38fd1498Szrj 				  _RandomAccessIterator>)
1803*38fd1498Szrj       __glibcxx_function_requires(_ConvertibleConcept<_InputValueType,
1804*38fd1498Szrj 				  _OutputValueType>)
1805*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
1806*38fd1498Szrj 				  _InputValueType, _OutputValueType>)
1807*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
1808*38fd1498Szrj 				  _OutputValueType, _OutputValueType>)
1809*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
1810*38fd1498Szrj       __glibcxx_requires_irreflexive_pred(__first, __last, __comp);
1811*38fd1498Szrj       __glibcxx_requires_valid_range(__result_first, __result_last);
1812*38fd1498Szrj 
1813*38fd1498Szrj       return std::__partial_sort_copy(__first, __last,
1814*38fd1498Szrj 				      __result_first, __result_last,
1815*38fd1498Szrj 				__gnu_cxx::__ops::__iter_comp_iter(__comp));
1816*38fd1498Szrj     }
1817*38fd1498Szrj 
1818*38fd1498Szrj   /// This is a helper function for the sort routine.
1819*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
1820*38fd1498Szrj     void
1821*38fd1498Szrj     __unguarded_linear_insert(_RandomAccessIterator __last,
1822*38fd1498Szrj 			      _Compare __comp)
1823*38fd1498Szrj     {
1824*38fd1498Szrj       typename iterator_traits<_RandomAccessIterator>::value_type
1825*38fd1498Szrj 	__val = _GLIBCXX_MOVE(*__last);
1826*38fd1498Szrj       _RandomAccessIterator __next = __last;
1827*38fd1498Szrj       --__next;
1828*38fd1498Szrj       while (__comp(__val, __next))
1829*38fd1498Szrj 	{
1830*38fd1498Szrj 	  *__last = _GLIBCXX_MOVE(*__next);
1831*38fd1498Szrj 	  __last = __next;
1832*38fd1498Szrj 	  --__next;
1833*38fd1498Szrj 	}
1834*38fd1498Szrj       *__last = _GLIBCXX_MOVE(__val);
1835*38fd1498Szrj     }
1836*38fd1498Szrj 
1837*38fd1498Szrj   /// This is a helper function for the sort routine.
1838*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
1839*38fd1498Szrj     void
1840*38fd1498Szrj     __insertion_sort(_RandomAccessIterator __first,
1841*38fd1498Szrj 		     _RandomAccessIterator __last, _Compare __comp)
1842*38fd1498Szrj     {
1843*38fd1498Szrj       if (__first == __last) return;
1844*38fd1498Szrj 
1845*38fd1498Szrj       for (_RandomAccessIterator __i = __first + 1; __i != __last; ++__i)
1846*38fd1498Szrj 	{
1847*38fd1498Szrj 	  if (__comp(__i, __first))
1848*38fd1498Szrj 	    {
1849*38fd1498Szrj 	      typename iterator_traits<_RandomAccessIterator>::value_type
1850*38fd1498Szrj 		__val = _GLIBCXX_MOVE(*__i);
1851*38fd1498Szrj 	      _GLIBCXX_MOVE_BACKWARD3(__first, __i, __i + 1);
1852*38fd1498Szrj 	      *__first = _GLIBCXX_MOVE(__val);
1853*38fd1498Szrj 	    }
1854*38fd1498Szrj 	  else
1855*38fd1498Szrj 	    std::__unguarded_linear_insert(__i,
1856*38fd1498Szrj 				__gnu_cxx::__ops::__val_comp_iter(__comp));
1857*38fd1498Szrj 	}
1858*38fd1498Szrj     }
1859*38fd1498Szrj 
1860*38fd1498Szrj   /// This is a helper function for the sort routine.
1861*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
1862*38fd1498Szrj     inline void
1863*38fd1498Szrj     __unguarded_insertion_sort(_RandomAccessIterator __first,
1864*38fd1498Szrj 			       _RandomAccessIterator __last, _Compare __comp)
1865*38fd1498Szrj     {
1866*38fd1498Szrj       for (_RandomAccessIterator __i = __first; __i != __last; ++__i)
1867*38fd1498Szrj 	std::__unguarded_linear_insert(__i,
1868*38fd1498Szrj 				__gnu_cxx::__ops::__val_comp_iter(__comp));
1869*38fd1498Szrj     }
1870*38fd1498Szrj 
1871*38fd1498Szrj   /**
1872*38fd1498Szrj    *  @doctodo
1873*38fd1498Szrj    *  This controls some aspect of the sort routines.
1874*38fd1498Szrj   */
1875*38fd1498Szrj   enum { _S_threshold = 16 };
1876*38fd1498Szrj 
1877*38fd1498Szrj   /// This is a helper function for the sort routine.
1878*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
1879*38fd1498Szrj     void
1880*38fd1498Szrj     __final_insertion_sort(_RandomAccessIterator __first,
1881*38fd1498Szrj 			   _RandomAccessIterator __last, _Compare __comp)
1882*38fd1498Szrj     {
1883*38fd1498Szrj       if (__last - __first > int(_S_threshold))
1884*38fd1498Szrj 	{
1885*38fd1498Szrj 	  std::__insertion_sort(__first, __first + int(_S_threshold), __comp);
1886*38fd1498Szrj 	  std::__unguarded_insertion_sort(__first + int(_S_threshold), __last,
1887*38fd1498Szrj 					  __comp);
1888*38fd1498Szrj 	}
1889*38fd1498Szrj       else
1890*38fd1498Szrj 	std::__insertion_sort(__first, __last, __comp);
1891*38fd1498Szrj     }
1892*38fd1498Szrj 
1893*38fd1498Szrj   /// This is a helper function...
1894*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
1895*38fd1498Szrj     _RandomAccessIterator
1896*38fd1498Szrj     __unguarded_partition(_RandomAccessIterator __first,
1897*38fd1498Szrj 			  _RandomAccessIterator __last,
1898*38fd1498Szrj 			  _RandomAccessIterator __pivot, _Compare __comp)
1899*38fd1498Szrj     {
1900*38fd1498Szrj       while (true)
1901*38fd1498Szrj 	{
1902*38fd1498Szrj 	  while (__comp(__first, __pivot))
1903*38fd1498Szrj 	    ++__first;
1904*38fd1498Szrj 	  --__last;
1905*38fd1498Szrj 	  while (__comp(__pivot, __last))
1906*38fd1498Szrj 	    --__last;
1907*38fd1498Szrj 	  if (!(__first < __last))
1908*38fd1498Szrj 	    return __first;
1909*38fd1498Szrj 	  std::iter_swap(__first, __last);
1910*38fd1498Szrj 	  ++__first;
1911*38fd1498Szrj 	}
1912*38fd1498Szrj     }
1913*38fd1498Szrj 
1914*38fd1498Szrj   /// This is a helper function...
1915*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
1916*38fd1498Szrj     inline _RandomAccessIterator
1917*38fd1498Szrj     __unguarded_partition_pivot(_RandomAccessIterator __first,
1918*38fd1498Szrj 				_RandomAccessIterator __last, _Compare __comp)
1919*38fd1498Szrj     {
1920*38fd1498Szrj       _RandomAccessIterator __mid = __first + (__last - __first) / 2;
1921*38fd1498Szrj       std::__move_median_to_first(__first, __first + 1, __mid, __last - 1,
1922*38fd1498Szrj 				  __comp);
1923*38fd1498Szrj       return std::__unguarded_partition(__first + 1, __last, __first, __comp);
1924*38fd1498Szrj     }
1925*38fd1498Szrj 
1926*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
1927*38fd1498Szrj     inline void
1928*38fd1498Szrj     __partial_sort(_RandomAccessIterator __first,
1929*38fd1498Szrj 		   _RandomAccessIterator __middle,
1930*38fd1498Szrj 		   _RandomAccessIterator __last,
1931*38fd1498Szrj 		   _Compare __comp)
1932*38fd1498Szrj     {
1933*38fd1498Szrj       std::__heap_select(__first, __middle, __last, __comp);
1934*38fd1498Szrj       std::__sort_heap(__first, __middle, __comp);
1935*38fd1498Szrj     }
1936*38fd1498Szrj 
1937*38fd1498Szrj   /// This is a helper function for the sort routine.
1938*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Size, typename _Compare>
1939*38fd1498Szrj     void
1940*38fd1498Szrj     __introsort_loop(_RandomAccessIterator __first,
1941*38fd1498Szrj 		     _RandomAccessIterator __last,
1942*38fd1498Szrj 		     _Size __depth_limit, _Compare __comp)
1943*38fd1498Szrj     {
1944*38fd1498Szrj       while (__last - __first > int(_S_threshold))
1945*38fd1498Szrj 	{
1946*38fd1498Szrj 	  if (__depth_limit == 0)
1947*38fd1498Szrj 	    {
1948*38fd1498Szrj 	      std::__partial_sort(__first, __last, __last, __comp);
1949*38fd1498Szrj 	      return;
1950*38fd1498Szrj 	    }
1951*38fd1498Szrj 	  --__depth_limit;
1952*38fd1498Szrj 	  _RandomAccessIterator __cut =
1953*38fd1498Szrj 	    std::__unguarded_partition_pivot(__first, __last, __comp);
1954*38fd1498Szrj 	  std::__introsort_loop(__cut, __last, __depth_limit, __comp);
1955*38fd1498Szrj 	  __last = __cut;
1956*38fd1498Szrj 	}
1957*38fd1498Szrj     }
1958*38fd1498Szrj 
1959*38fd1498Szrj   // sort
1960*38fd1498Szrj 
1961*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
1962*38fd1498Szrj     inline void
1963*38fd1498Szrj     __sort(_RandomAccessIterator __first, _RandomAccessIterator __last,
1964*38fd1498Szrj 	   _Compare __comp)
1965*38fd1498Szrj     {
1966*38fd1498Szrj       if (__first != __last)
1967*38fd1498Szrj 	{
1968*38fd1498Szrj 	  std::__introsort_loop(__first, __last,
1969*38fd1498Szrj 				std::__lg(__last - __first) * 2,
1970*38fd1498Szrj 				__comp);
1971*38fd1498Szrj 	  std::__final_insertion_sort(__first, __last, __comp);
1972*38fd1498Szrj 	}
1973*38fd1498Szrj     }
1974*38fd1498Szrj 
1975*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Size, typename _Compare>
1976*38fd1498Szrj     void
1977*38fd1498Szrj     __introselect(_RandomAccessIterator __first, _RandomAccessIterator __nth,
1978*38fd1498Szrj 		  _RandomAccessIterator __last, _Size __depth_limit,
1979*38fd1498Szrj 		  _Compare __comp)
1980*38fd1498Szrj     {
1981*38fd1498Szrj       while (__last - __first > 3)
1982*38fd1498Szrj 	{
1983*38fd1498Szrj 	  if (__depth_limit == 0)
1984*38fd1498Szrj 	    {
1985*38fd1498Szrj 	      std::__heap_select(__first, __nth + 1, __last, __comp);
1986*38fd1498Szrj 	      // Place the nth largest element in its final position.
1987*38fd1498Szrj 	      std::iter_swap(__first, __nth);
1988*38fd1498Szrj 	      return;
1989*38fd1498Szrj 	    }
1990*38fd1498Szrj 	  --__depth_limit;
1991*38fd1498Szrj 	  _RandomAccessIterator __cut =
1992*38fd1498Szrj 	    std::__unguarded_partition_pivot(__first, __last, __comp);
1993*38fd1498Szrj 	  if (__cut <= __nth)
1994*38fd1498Szrj 	    __first = __cut;
1995*38fd1498Szrj 	  else
1996*38fd1498Szrj 	    __last = __cut;
1997*38fd1498Szrj 	}
1998*38fd1498Szrj       std::__insertion_sort(__first, __last, __comp);
1999*38fd1498Szrj     }
2000*38fd1498Szrj 
2001*38fd1498Szrj   // nth_element
2002*38fd1498Szrj 
2003*38fd1498Szrj   // lower_bound moved to stl_algobase.h
2004*38fd1498Szrj 
2005*38fd1498Szrj   /**
2006*38fd1498Szrj    *  @brief Finds the first position in which @p __val could be inserted
2007*38fd1498Szrj    *         without changing the ordering.
2008*38fd1498Szrj    *  @ingroup binary_search_algorithms
2009*38fd1498Szrj    *  @param  __first   An iterator.
2010*38fd1498Szrj    *  @param  __last    Another iterator.
2011*38fd1498Szrj    *  @param  __val     The search term.
2012*38fd1498Szrj    *  @param  __comp    A functor to use for comparisons.
2013*38fd1498Szrj    *  @return An iterator pointing to the first element <em>not less
2014*38fd1498Szrj    *           than</em> @p __val, or end() if every element is less
2015*38fd1498Szrj    *           than @p __val.
2016*38fd1498Szrj    *  @ingroup binary_search_algorithms
2017*38fd1498Szrj    *
2018*38fd1498Szrj    *  The comparison function should have the same effects on ordering as
2019*38fd1498Szrj    *  the function used for the initial sort.
2020*38fd1498Szrj   */
2021*38fd1498Szrj   template<typename _ForwardIterator, typename _Tp, typename _Compare>
2022*38fd1498Szrj     inline _ForwardIterator
2023*38fd1498Szrj     lower_bound(_ForwardIterator __first, _ForwardIterator __last,
2024*38fd1498Szrj 		const _Tp& __val, _Compare __comp)
2025*38fd1498Szrj     {
2026*38fd1498Szrj       // concept requirements
2027*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
2028*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
2029*38fd1498Szrj 	typename iterator_traits<_ForwardIterator>::value_type, _Tp>)
2030*38fd1498Szrj       __glibcxx_requires_partitioned_lower_pred(__first, __last,
2031*38fd1498Szrj 						__val, __comp);
2032*38fd1498Szrj 
2033*38fd1498Szrj       return std::__lower_bound(__first, __last, __val,
2034*38fd1498Szrj 				__gnu_cxx::__ops::__iter_comp_val(__comp));
2035*38fd1498Szrj     }
2036*38fd1498Szrj 
2037*38fd1498Szrj   template<typename _ForwardIterator, typename _Tp, typename _Compare>
2038*38fd1498Szrj     _ForwardIterator
2039*38fd1498Szrj     __upper_bound(_ForwardIterator __first, _ForwardIterator __last,
2040*38fd1498Szrj 		  const _Tp& __val, _Compare __comp)
2041*38fd1498Szrj     {
2042*38fd1498Szrj       typedef typename iterator_traits<_ForwardIterator>::difference_type
2043*38fd1498Szrj 	_DistanceType;
2044*38fd1498Szrj 
2045*38fd1498Szrj       _DistanceType __len = std::distance(__first, __last);
2046*38fd1498Szrj 
2047*38fd1498Szrj       while (__len > 0)
2048*38fd1498Szrj 	{
2049*38fd1498Szrj 	  _DistanceType __half = __len >> 1;
2050*38fd1498Szrj 	  _ForwardIterator __middle = __first;
2051*38fd1498Szrj 	  std::advance(__middle, __half);
2052*38fd1498Szrj 	  if (__comp(__val, __middle))
2053*38fd1498Szrj 	    __len = __half;
2054*38fd1498Szrj 	  else
2055*38fd1498Szrj 	    {
2056*38fd1498Szrj 	      __first = __middle;
2057*38fd1498Szrj 	      ++__first;
2058*38fd1498Szrj 	      __len = __len - __half - 1;
2059*38fd1498Szrj 	    }
2060*38fd1498Szrj 	}
2061*38fd1498Szrj       return __first;
2062*38fd1498Szrj     }
2063*38fd1498Szrj 
2064*38fd1498Szrj   /**
2065*38fd1498Szrj    *  @brief Finds the last position in which @p __val could be inserted
2066*38fd1498Szrj    *         without changing the ordering.
2067*38fd1498Szrj    *  @ingroup binary_search_algorithms
2068*38fd1498Szrj    *  @param  __first   An iterator.
2069*38fd1498Szrj    *  @param  __last    Another iterator.
2070*38fd1498Szrj    *  @param  __val     The search term.
2071*38fd1498Szrj    *  @return  An iterator pointing to the first element greater than @p __val,
2072*38fd1498Szrj    *           or end() if no elements are greater than @p __val.
2073*38fd1498Szrj    *  @ingroup binary_search_algorithms
2074*38fd1498Szrj   */
2075*38fd1498Szrj   template<typename _ForwardIterator, typename _Tp>
2076*38fd1498Szrj     inline _ForwardIterator
2077*38fd1498Szrj     upper_bound(_ForwardIterator __first, _ForwardIterator __last,
2078*38fd1498Szrj 		const _Tp& __val)
2079*38fd1498Szrj     {
2080*38fd1498Szrj       // concept requirements
2081*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
2082*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
2083*38fd1498Szrj 	_Tp, typename iterator_traits<_ForwardIterator>::value_type>)
2084*38fd1498Szrj       __glibcxx_requires_partitioned_upper(__first, __last, __val);
2085*38fd1498Szrj 
2086*38fd1498Szrj       return std::__upper_bound(__first, __last, __val,
2087*38fd1498Szrj 				__gnu_cxx::__ops::__val_less_iter());
2088*38fd1498Szrj     }
2089*38fd1498Szrj 
2090*38fd1498Szrj   /**
2091*38fd1498Szrj    *  @brief Finds the last position in which @p __val could be inserted
2092*38fd1498Szrj    *         without changing the ordering.
2093*38fd1498Szrj    *  @ingroup binary_search_algorithms
2094*38fd1498Szrj    *  @param  __first   An iterator.
2095*38fd1498Szrj    *  @param  __last    Another iterator.
2096*38fd1498Szrj    *  @param  __val     The search term.
2097*38fd1498Szrj    *  @param  __comp    A functor to use for comparisons.
2098*38fd1498Szrj    *  @return  An iterator pointing to the first element greater than @p __val,
2099*38fd1498Szrj    *           or end() if no elements are greater than @p __val.
2100*38fd1498Szrj    *  @ingroup binary_search_algorithms
2101*38fd1498Szrj    *
2102*38fd1498Szrj    *  The comparison function should have the same effects on ordering as
2103*38fd1498Szrj    *  the function used for the initial sort.
2104*38fd1498Szrj   */
2105*38fd1498Szrj   template<typename _ForwardIterator, typename _Tp, typename _Compare>
2106*38fd1498Szrj     inline _ForwardIterator
2107*38fd1498Szrj     upper_bound(_ForwardIterator __first, _ForwardIterator __last,
2108*38fd1498Szrj 		const _Tp& __val, _Compare __comp)
2109*38fd1498Szrj     {
2110*38fd1498Szrj       // concept requirements
2111*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
2112*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
2113*38fd1498Szrj 	_Tp, typename iterator_traits<_ForwardIterator>::value_type>)
2114*38fd1498Szrj       __glibcxx_requires_partitioned_upper_pred(__first, __last,
2115*38fd1498Szrj 						__val, __comp);
2116*38fd1498Szrj 
2117*38fd1498Szrj       return std::__upper_bound(__first, __last, __val,
2118*38fd1498Szrj 				__gnu_cxx::__ops::__val_comp_iter(__comp));
2119*38fd1498Szrj     }
2120*38fd1498Szrj 
2121*38fd1498Szrj   template<typename _ForwardIterator, typename _Tp,
2122*38fd1498Szrj 	   typename _CompareItTp, typename _CompareTpIt>
2123*38fd1498Szrj     pair<_ForwardIterator, _ForwardIterator>
2124*38fd1498Szrj     __equal_range(_ForwardIterator __first, _ForwardIterator __last,
2125*38fd1498Szrj 		  const _Tp& __val,
2126*38fd1498Szrj 		  _CompareItTp __comp_it_val, _CompareTpIt __comp_val_it)
2127*38fd1498Szrj     {
2128*38fd1498Szrj       typedef typename iterator_traits<_ForwardIterator>::difference_type
2129*38fd1498Szrj 	_DistanceType;
2130*38fd1498Szrj 
2131*38fd1498Szrj       _DistanceType __len = std::distance(__first, __last);
2132*38fd1498Szrj 
2133*38fd1498Szrj       while (__len > 0)
2134*38fd1498Szrj 	{
2135*38fd1498Szrj 	  _DistanceType __half = __len >> 1;
2136*38fd1498Szrj 	  _ForwardIterator __middle = __first;
2137*38fd1498Szrj 	  std::advance(__middle, __half);
2138*38fd1498Szrj 	  if (__comp_it_val(__middle, __val))
2139*38fd1498Szrj 	    {
2140*38fd1498Szrj 	      __first = __middle;
2141*38fd1498Szrj 	      ++__first;
2142*38fd1498Szrj 	      __len = __len - __half - 1;
2143*38fd1498Szrj 	    }
2144*38fd1498Szrj 	  else if (__comp_val_it(__val, __middle))
2145*38fd1498Szrj 	    __len = __half;
2146*38fd1498Szrj 	  else
2147*38fd1498Szrj 	    {
2148*38fd1498Szrj 	      _ForwardIterator __left
2149*38fd1498Szrj 		= std::__lower_bound(__first, __middle, __val, __comp_it_val);
2150*38fd1498Szrj 	      std::advance(__first, __len);
2151*38fd1498Szrj 	      _ForwardIterator __right
2152*38fd1498Szrj 		= std::__upper_bound(++__middle, __first, __val, __comp_val_it);
2153*38fd1498Szrj 	      return pair<_ForwardIterator, _ForwardIterator>(__left, __right);
2154*38fd1498Szrj 	    }
2155*38fd1498Szrj 	}
2156*38fd1498Szrj       return pair<_ForwardIterator, _ForwardIterator>(__first, __first);
2157*38fd1498Szrj     }
2158*38fd1498Szrj 
2159*38fd1498Szrj   /**
2160*38fd1498Szrj    *  @brief Finds the largest subrange in which @p __val could be inserted
2161*38fd1498Szrj    *         at any place in it without changing the ordering.
2162*38fd1498Szrj    *  @ingroup binary_search_algorithms
2163*38fd1498Szrj    *  @param  __first   An iterator.
2164*38fd1498Szrj    *  @param  __last    Another iterator.
2165*38fd1498Szrj    *  @param  __val     The search term.
2166*38fd1498Szrj    *  @return  An pair of iterators defining the subrange.
2167*38fd1498Szrj    *  @ingroup binary_search_algorithms
2168*38fd1498Szrj    *
2169*38fd1498Szrj    *  This is equivalent to
2170*38fd1498Szrj    *  @code
2171*38fd1498Szrj    *    std::make_pair(lower_bound(__first, __last, __val),
2172*38fd1498Szrj    *                   upper_bound(__first, __last, __val))
2173*38fd1498Szrj    *  @endcode
2174*38fd1498Szrj    *  but does not actually call those functions.
2175*38fd1498Szrj   */
2176*38fd1498Szrj   template<typename _ForwardIterator, typename _Tp>
2177*38fd1498Szrj     inline pair<_ForwardIterator, _ForwardIterator>
2178*38fd1498Szrj     equal_range(_ForwardIterator __first, _ForwardIterator __last,
2179*38fd1498Szrj 		const _Tp& __val)
2180*38fd1498Szrj     {
2181*38fd1498Szrj       // concept requirements
2182*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
2183*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
2184*38fd1498Szrj 	typename iterator_traits<_ForwardIterator>::value_type, _Tp>)
2185*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
2186*38fd1498Szrj 	_Tp, typename iterator_traits<_ForwardIterator>::value_type>)
2187*38fd1498Szrj       __glibcxx_requires_partitioned_lower(__first, __last, __val);
2188*38fd1498Szrj       __glibcxx_requires_partitioned_upper(__first, __last, __val);
2189*38fd1498Szrj 
2190*38fd1498Szrj       return std::__equal_range(__first, __last, __val,
2191*38fd1498Szrj 				__gnu_cxx::__ops::__iter_less_val(),
2192*38fd1498Szrj 				__gnu_cxx::__ops::__val_less_iter());
2193*38fd1498Szrj     }
2194*38fd1498Szrj 
2195*38fd1498Szrj   /**
2196*38fd1498Szrj    *  @brief Finds the largest subrange in which @p __val could be inserted
2197*38fd1498Szrj    *         at any place in it without changing the ordering.
2198*38fd1498Szrj    *  @param  __first   An iterator.
2199*38fd1498Szrj    *  @param  __last    Another iterator.
2200*38fd1498Szrj    *  @param  __val     The search term.
2201*38fd1498Szrj    *  @param  __comp    A functor to use for comparisons.
2202*38fd1498Szrj    *  @return  An pair of iterators defining the subrange.
2203*38fd1498Szrj    *  @ingroup binary_search_algorithms
2204*38fd1498Szrj    *
2205*38fd1498Szrj    *  This is equivalent to
2206*38fd1498Szrj    *  @code
2207*38fd1498Szrj    *    std::make_pair(lower_bound(__first, __last, __val, __comp),
2208*38fd1498Szrj    *                   upper_bound(__first, __last, __val, __comp))
2209*38fd1498Szrj    *  @endcode
2210*38fd1498Szrj    *  but does not actually call those functions.
2211*38fd1498Szrj   */
2212*38fd1498Szrj   template<typename _ForwardIterator, typename _Tp, typename _Compare>
2213*38fd1498Szrj     inline pair<_ForwardIterator, _ForwardIterator>
2214*38fd1498Szrj     equal_range(_ForwardIterator __first, _ForwardIterator __last,
2215*38fd1498Szrj 		const _Tp& __val, _Compare __comp)
2216*38fd1498Szrj     {
2217*38fd1498Szrj       // concept requirements
2218*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
2219*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
2220*38fd1498Szrj 	typename iterator_traits<_ForwardIterator>::value_type, _Tp>)
2221*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
2222*38fd1498Szrj 	_Tp, typename iterator_traits<_ForwardIterator>::value_type>)
2223*38fd1498Szrj       __glibcxx_requires_partitioned_lower_pred(__first, __last,
2224*38fd1498Szrj 						__val, __comp);
2225*38fd1498Szrj       __glibcxx_requires_partitioned_upper_pred(__first, __last,
2226*38fd1498Szrj 						__val, __comp);
2227*38fd1498Szrj 
2228*38fd1498Szrj       return std::__equal_range(__first, __last, __val,
2229*38fd1498Szrj 				__gnu_cxx::__ops::__iter_comp_val(__comp),
2230*38fd1498Szrj 				__gnu_cxx::__ops::__val_comp_iter(__comp));
2231*38fd1498Szrj     }
2232*38fd1498Szrj 
2233*38fd1498Szrj   /**
2234*38fd1498Szrj    *  @brief Determines whether an element exists in a range.
2235*38fd1498Szrj    *  @ingroup binary_search_algorithms
2236*38fd1498Szrj    *  @param  __first   An iterator.
2237*38fd1498Szrj    *  @param  __last    Another iterator.
2238*38fd1498Szrj    *  @param  __val     The search term.
2239*38fd1498Szrj    *  @return True if @p __val (or its equivalent) is in [@p
2240*38fd1498Szrj    *  __first,@p __last ].
2241*38fd1498Szrj    *
2242*38fd1498Szrj    *  Note that this does not actually return an iterator to @p __val.  For
2243*38fd1498Szrj    *  that, use std::find or a container's specialized find member functions.
2244*38fd1498Szrj   */
2245*38fd1498Szrj   template<typename _ForwardIterator, typename _Tp>
2246*38fd1498Szrj     bool
2247*38fd1498Szrj     binary_search(_ForwardIterator __first, _ForwardIterator __last,
2248*38fd1498Szrj 		  const _Tp& __val)
2249*38fd1498Szrj     {
2250*38fd1498Szrj       // concept requirements
2251*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
2252*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
2253*38fd1498Szrj 	_Tp, typename iterator_traits<_ForwardIterator>::value_type>)
2254*38fd1498Szrj       __glibcxx_requires_partitioned_lower(__first, __last, __val);
2255*38fd1498Szrj       __glibcxx_requires_partitioned_upper(__first, __last, __val);
2256*38fd1498Szrj 
2257*38fd1498Szrj       _ForwardIterator __i
2258*38fd1498Szrj 	= std::__lower_bound(__first, __last, __val,
2259*38fd1498Szrj 			     __gnu_cxx::__ops::__iter_less_val());
2260*38fd1498Szrj       return __i != __last && !(__val < *__i);
2261*38fd1498Szrj     }
2262*38fd1498Szrj 
2263*38fd1498Szrj   /**
2264*38fd1498Szrj    *  @brief Determines whether an element exists in a range.
2265*38fd1498Szrj    *  @ingroup binary_search_algorithms
2266*38fd1498Szrj    *  @param  __first   An iterator.
2267*38fd1498Szrj    *  @param  __last    Another iterator.
2268*38fd1498Szrj    *  @param  __val     The search term.
2269*38fd1498Szrj    *  @param  __comp    A functor to use for comparisons.
2270*38fd1498Szrj    *  @return  True if @p __val (or its equivalent) is in @p [__first,__last].
2271*38fd1498Szrj    *
2272*38fd1498Szrj    *  Note that this does not actually return an iterator to @p __val.  For
2273*38fd1498Szrj    *  that, use std::find or a container's specialized find member functions.
2274*38fd1498Szrj    *
2275*38fd1498Szrj    *  The comparison function should have the same effects on ordering as
2276*38fd1498Szrj    *  the function used for the initial sort.
2277*38fd1498Szrj   */
2278*38fd1498Szrj   template<typename _ForwardIterator, typename _Tp, typename _Compare>
2279*38fd1498Szrj     bool
2280*38fd1498Szrj     binary_search(_ForwardIterator __first, _ForwardIterator __last,
2281*38fd1498Szrj 		  const _Tp& __val, _Compare __comp)
2282*38fd1498Szrj     {
2283*38fd1498Szrj       // concept requirements
2284*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
2285*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
2286*38fd1498Szrj 	_Tp, typename iterator_traits<_ForwardIterator>::value_type>)
2287*38fd1498Szrj       __glibcxx_requires_partitioned_lower_pred(__first, __last,
2288*38fd1498Szrj 						__val, __comp);
2289*38fd1498Szrj       __glibcxx_requires_partitioned_upper_pred(__first, __last,
2290*38fd1498Szrj 						__val, __comp);
2291*38fd1498Szrj 
2292*38fd1498Szrj       _ForwardIterator __i
2293*38fd1498Szrj 	= std::__lower_bound(__first, __last, __val,
2294*38fd1498Szrj 			     __gnu_cxx::__ops::__iter_comp_val(__comp));
2295*38fd1498Szrj       return __i != __last && !bool(__comp(__val, *__i));
2296*38fd1498Szrj     }
2297*38fd1498Szrj 
2298*38fd1498Szrj   // merge
2299*38fd1498Szrj 
2300*38fd1498Szrj   /// This is a helper function for the __merge_adaptive routines.
2301*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
2302*38fd1498Szrj 	   typename _OutputIterator, typename _Compare>
2303*38fd1498Szrj     void
2304*38fd1498Szrj     __move_merge_adaptive(_InputIterator1 __first1, _InputIterator1 __last1,
2305*38fd1498Szrj 			  _InputIterator2 __first2, _InputIterator2 __last2,
2306*38fd1498Szrj 			  _OutputIterator __result, _Compare __comp)
2307*38fd1498Szrj     {
2308*38fd1498Szrj       while (__first1 != __last1 && __first2 != __last2)
2309*38fd1498Szrj 	{
2310*38fd1498Szrj 	  if (__comp(__first2, __first1))
2311*38fd1498Szrj 	    {
2312*38fd1498Szrj 	      *__result = _GLIBCXX_MOVE(*__first2);
2313*38fd1498Szrj 	      ++__first2;
2314*38fd1498Szrj 	    }
2315*38fd1498Szrj 	  else
2316*38fd1498Szrj 	    {
2317*38fd1498Szrj 	      *__result = _GLIBCXX_MOVE(*__first1);
2318*38fd1498Szrj 	      ++__first1;
2319*38fd1498Szrj 	    }
2320*38fd1498Szrj 	  ++__result;
2321*38fd1498Szrj 	}
2322*38fd1498Szrj       if (__first1 != __last1)
2323*38fd1498Szrj 	_GLIBCXX_MOVE3(__first1, __last1, __result);
2324*38fd1498Szrj     }
2325*38fd1498Szrj 
2326*38fd1498Szrj   /// This is a helper function for the __merge_adaptive routines.
2327*38fd1498Szrj   template<typename _BidirectionalIterator1, typename _BidirectionalIterator2,
2328*38fd1498Szrj 	   typename _BidirectionalIterator3, typename _Compare>
2329*38fd1498Szrj     void
2330*38fd1498Szrj     __move_merge_adaptive_backward(_BidirectionalIterator1 __first1,
2331*38fd1498Szrj 				   _BidirectionalIterator1 __last1,
2332*38fd1498Szrj 				   _BidirectionalIterator2 __first2,
2333*38fd1498Szrj 				   _BidirectionalIterator2 __last2,
2334*38fd1498Szrj 				   _BidirectionalIterator3 __result,
2335*38fd1498Szrj 				   _Compare __comp)
2336*38fd1498Szrj     {
2337*38fd1498Szrj       if (__first1 == __last1)
2338*38fd1498Szrj 	{
2339*38fd1498Szrj 	  _GLIBCXX_MOVE_BACKWARD3(__first2, __last2, __result);
2340*38fd1498Szrj 	  return;
2341*38fd1498Szrj 	}
2342*38fd1498Szrj       else if (__first2 == __last2)
2343*38fd1498Szrj 	return;
2344*38fd1498Szrj 
2345*38fd1498Szrj       --__last1;
2346*38fd1498Szrj       --__last2;
2347*38fd1498Szrj       while (true)
2348*38fd1498Szrj 	{
2349*38fd1498Szrj 	  if (__comp(__last2, __last1))
2350*38fd1498Szrj 	    {
2351*38fd1498Szrj 	      *--__result = _GLIBCXX_MOVE(*__last1);
2352*38fd1498Szrj 	      if (__first1 == __last1)
2353*38fd1498Szrj 		{
2354*38fd1498Szrj 		  _GLIBCXX_MOVE_BACKWARD3(__first2, ++__last2, __result);
2355*38fd1498Szrj 		  return;
2356*38fd1498Szrj 		}
2357*38fd1498Szrj 	      --__last1;
2358*38fd1498Szrj 	    }
2359*38fd1498Szrj 	  else
2360*38fd1498Szrj 	    {
2361*38fd1498Szrj 	      *--__result = _GLIBCXX_MOVE(*__last2);
2362*38fd1498Szrj 	      if (__first2 == __last2)
2363*38fd1498Szrj 		return;
2364*38fd1498Szrj 	      --__last2;
2365*38fd1498Szrj 	    }
2366*38fd1498Szrj 	}
2367*38fd1498Szrj     }
2368*38fd1498Szrj 
2369*38fd1498Szrj   /// This is a helper function for the merge routines.
2370*38fd1498Szrj   template<typename _BidirectionalIterator1, typename _BidirectionalIterator2,
2371*38fd1498Szrj 	   typename _Distance>
2372*38fd1498Szrj     _BidirectionalIterator1
2373*38fd1498Szrj     __rotate_adaptive(_BidirectionalIterator1 __first,
2374*38fd1498Szrj 		      _BidirectionalIterator1 __middle,
2375*38fd1498Szrj 		      _BidirectionalIterator1 __last,
2376*38fd1498Szrj 		      _Distance __len1, _Distance __len2,
2377*38fd1498Szrj 		      _BidirectionalIterator2 __buffer,
2378*38fd1498Szrj 		      _Distance __buffer_size)
2379*38fd1498Szrj     {
2380*38fd1498Szrj       _BidirectionalIterator2 __buffer_end;
2381*38fd1498Szrj       if (__len1 > __len2 && __len2 <= __buffer_size)
2382*38fd1498Szrj 	{
2383*38fd1498Szrj 	  if (__len2)
2384*38fd1498Szrj 	    {
2385*38fd1498Szrj 	      __buffer_end = _GLIBCXX_MOVE3(__middle, __last, __buffer);
2386*38fd1498Szrj 	      _GLIBCXX_MOVE_BACKWARD3(__first, __middle, __last);
2387*38fd1498Szrj 	      return _GLIBCXX_MOVE3(__buffer, __buffer_end, __first);
2388*38fd1498Szrj 	    }
2389*38fd1498Szrj 	  else
2390*38fd1498Szrj 	    return __first;
2391*38fd1498Szrj 	}
2392*38fd1498Szrj       else if (__len1 <= __buffer_size)
2393*38fd1498Szrj 	{
2394*38fd1498Szrj 	  if (__len1)
2395*38fd1498Szrj 	    {
2396*38fd1498Szrj 	      __buffer_end = _GLIBCXX_MOVE3(__first, __middle, __buffer);
2397*38fd1498Szrj 	      _GLIBCXX_MOVE3(__middle, __last, __first);
2398*38fd1498Szrj 	      return _GLIBCXX_MOVE_BACKWARD3(__buffer, __buffer_end, __last);
2399*38fd1498Szrj 	    }
2400*38fd1498Szrj 	  else
2401*38fd1498Szrj 	    return __last;
2402*38fd1498Szrj 	}
2403*38fd1498Szrj       else
2404*38fd1498Szrj 	{
2405*38fd1498Szrj 	  std::rotate(__first, __middle, __last);
2406*38fd1498Szrj 	  std::advance(__first, std::distance(__middle, __last));
2407*38fd1498Szrj 	  return __first;
2408*38fd1498Szrj 	}
2409*38fd1498Szrj     }
2410*38fd1498Szrj 
2411*38fd1498Szrj   /// This is a helper function for the merge routines.
2412*38fd1498Szrj   template<typename _BidirectionalIterator, typename _Distance,
2413*38fd1498Szrj 	   typename _Pointer, typename _Compare>
2414*38fd1498Szrj     void
2415*38fd1498Szrj     __merge_adaptive(_BidirectionalIterator __first,
2416*38fd1498Szrj 		     _BidirectionalIterator __middle,
2417*38fd1498Szrj 		     _BidirectionalIterator __last,
2418*38fd1498Szrj 		     _Distance __len1, _Distance __len2,
2419*38fd1498Szrj 		     _Pointer __buffer, _Distance __buffer_size,
2420*38fd1498Szrj 		     _Compare __comp)
2421*38fd1498Szrj     {
2422*38fd1498Szrj       if (__len1 <= __len2 && __len1 <= __buffer_size)
2423*38fd1498Szrj 	{
2424*38fd1498Szrj 	  _Pointer __buffer_end = _GLIBCXX_MOVE3(__first, __middle, __buffer);
2425*38fd1498Szrj 	  std::__move_merge_adaptive(__buffer, __buffer_end, __middle, __last,
2426*38fd1498Szrj 				     __first, __comp);
2427*38fd1498Szrj 	}
2428*38fd1498Szrj       else if (__len2 <= __buffer_size)
2429*38fd1498Szrj 	{
2430*38fd1498Szrj 	  _Pointer __buffer_end = _GLIBCXX_MOVE3(__middle, __last, __buffer);
2431*38fd1498Szrj 	  std::__move_merge_adaptive_backward(__first, __middle, __buffer,
2432*38fd1498Szrj 					      __buffer_end, __last, __comp);
2433*38fd1498Szrj 	}
2434*38fd1498Szrj       else
2435*38fd1498Szrj 	{
2436*38fd1498Szrj 	  _BidirectionalIterator __first_cut = __first;
2437*38fd1498Szrj 	  _BidirectionalIterator __second_cut = __middle;
2438*38fd1498Szrj 	  _Distance __len11 = 0;
2439*38fd1498Szrj 	  _Distance __len22 = 0;
2440*38fd1498Szrj 	  if (__len1 > __len2)
2441*38fd1498Szrj 	    {
2442*38fd1498Szrj 	      __len11 = __len1 / 2;
2443*38fd1498Szrj 	      std::advance(__first_cut, __len11);
2444*38fd1498Szrj 	      __second_cut
2445*38fd1498Szrj 		= std::__lower_bound(__middle, __last, *__first_cut,
2446*38fd1498Szrj 				     __gnu_cxx::__ops::__iter_comp_val(__comp));
2447*38fd1498Szrj 	      __len22 = std::distance(__middle, __second_cut);
2448*38fd1498Szrj 	    }
2449*38fd1498Szrj 	  else
2450*38fd1498Szrj 	    {
2451*38fd1498Szrj 	      __len22 = __len2 / 2;
2452*38fd1498Szrj 	      std::advance(__second_cut, __len22);
2453*38fd1498Szrj 	      __first_cut
2454*38fd1498Szrj 		= std::__upper_bound(__first, __middle, *__second_cut,
2455*38fd1498Szrj 				     __gnu_cxx::__ops::__val_comp_iter(__comp));
2456*38fd1498Szrj 	      __len11 = std::distance(__first, __first_cut);
2457*38fd1498Szrj 	    }
2458*38fd1498Szrj 
2459*38fd1498Szrj 	  _BidirectionalIterator __new_middle
2460*38fd1498Szrj 	    = std::__rotate_adaptive(__first_cut, __middle, __second_cut,
2461*38fd1498Szrj 				     __len1 - __len11, __len22, __buffer,
2462*38fd1498Szrj 				     __buffer_size);
2463*38fd1498Szrj 	  std::__merge_adaptive(__first, __first_cut, __new_middle, __len11,
2464*38fd1498Szrj 				__len22, __buffer, __buffer_size, __comp);
2465*38fd1498Szrj 	  std::__merge_adaptive(__new_middle, __second_cut, __last,
2466*38fd1498Szrj 				__len1 - __len11,
2467*38fd1498Szrj 				__len2 - __len22, __buffer,
2468*38fd1498Szrj 				__buffer_size, __comp);
2469*38fd1498Szrj 	}
2470*38fd1498Szrj     }
2471*38fd1498Szrj 
2472*38fd1498Szrj   /// This is a helper function for the merge routines.
2473*38fd1498Szrj   template<typename _BidirectionalIterator, typename _Distance,
2474*38fd1498Szrj 	   typename _Compare>
2475*38fd1498Szrj     void
2476*38fd1498Szrj     __merge_without_buffer(_BidirectionalIterator __first,
2477*38fd1498Szrj 			   _BidirectionalIterator __middle,
2478*38fd1498Szrj 			   _BidirectionalIterator __last,
2479*38fd1498Szrj 			   _Distance __len1, _Distance __len2,
2480*38fd1498Szrj 			   _Compare __comp)
2481*38fd1498Szrj     {
2482*38fd1498Szrj       if (__len1 == 0 || __len2 == 0)
2483*38fd1498Szrj 	return;
2484*38fd1498Szrj 
2485*38fd1498Szrj       if (__len1 + __len2 == 2)
2486*38fd1498Szrj 	{
2487*38fd1498Szrj 	  if (__comp(__middle, __first))
2488*38fd1498Szrj 	    std::iter_swap(__first, __middle);
2489*38fd1498Szrj 	  return;
2490*38fd1498Szrj 	}
2491*38fd1498Szrj 
2492*38fd1498Szrj       _BidirectionalIterator __first_cut = __first;
2493*38fd1498Szrj       _BidirectionalIterator __second_cut = __middle;
2494*38fd1498Szrj       _Distance __len11 = 0;
2495*38fd1498Szrj       _Distance __len22 = 0;
2496*38fd1498Szrj       if (__len1 > __len2)
2497*38fd1498Szrj 	{
2498*38fd1498Szrj 	  __len11 = __len1 / 2;
2499*38fd1498Szrj 	  std::advance(__first_cut, __len11);
2500*38fd1498Szrj 	  __second_cut
2501*38fd1498Szrj 	    = std::__lower_bound(__middle, __last, *__first_cut,
2502*38fd1498Szrj 				 __gnu_cxx::__ops::__iter_comp_val(__comp));
2503*38fd1498Szrj 	  __len22 = std::distance(__middle, __second_cut);
2504*38fd1498Szrj 	}
2505*38fd1498Szrj       else
2506*38fd1498Szrj 	{
2507*38fd1498Szrj 	  __len22 = __len2 / 2;
2508*38fd1498Szrj 	  std::advance(__second_cut, __len22);
2509*38fd1498Szrj 	  __first_cut
2510*38fd1498Szrj 	    = std::__upper_bound(__first, __middle, *__second_cut,
2511*38fd1498Szrj 				 __gnu_cxx::__ops::__val_comp_iter(__comp));
2512*38fd1498Szrj 	  __len11 = std::distance(__first, __first_cut);
2513*38fd1498Szrj 	}
2514*38fd1498Szrj 
2515*38fd1498Szrj       std::rotate(__first_cut, __middle, __second_cut);
2516*38fd1498Szrj       _BidirectionalIterator __new_middle = __first_cut;
2517*38fd1498Szrj       std::advance(__new_middle, std::distance(__middle, __second_cut));
2518*38fd1498Szrj       std::__merge_without_buffer(__first, __first_cut, __new_middle,
2519*38fd1498Szrj 				  __len11, __len22, __comp);
2520*38fd1498Szrj       std::__merge_without_buffer(__new_middle, __second_cut, __last,
2521*38fd1498Szrj 				  __len1 - __len11, __len2 - __len22, __comp);
2522*38fd1498Szrj     }
2523*38fd1498Szrj 
2524*38fd1498Szrj   template<typename _BidirectionalIterator, typename _Compare>
2525*38fd1498Szrj     void
2526*38fd1498Szrj     __inplace_merge(_BidirectionalIterator __first,
2527*38fd1498Szrj 		    _BidirectionalIterator __middle,
2528*38fd1498Szrj 		    _BidirectionalIterator __last,
2529*38fd1498Szrj 		    _Compare __comp)
2530*38fd1498Szrj     {
2531*38fd1498Szrj       typedef typename iterator_traits<_BidirectionalIterator>::value_type
2532*38fd1498Szrj 	  _ValueType;
2533*38fd1498Szrj       typedef typename iterator_traits<_BidirectionalIterator>::difference_type
2534*38fd1498Szrj 	  _DistanceType;
2535*38fd1498Szrj 
2536*38fd1498Szrj       if (__first == __middle || __middle == __last)
2537*38fd1498Szrj 	return;
2538*38fd1498Szrj 
2539*38fd1498Szrj       const _DistanceType __len1 = std::distance(__first, __middle);
2540*38fd1498Szrj       const _DistanceType __len2 = std::distance(__middle, __last);
2541*38fd1498Szrj 
2542*38fd1498Szrj       typedef _Temporary_buffer<_BidirectionalIterator, _ValueType> _TmpBuf;
2543*38fd1498Szrj       _TmpBuf __buf(__first, __last);
2544*38fd1498Szrj 
2545*38fd1498Szrj       if (__buf.begin() == 0)
2546*38fd1498Szrj 	std::__merge_without_buffer
2547*38fd1498Szrj 	  (__first, __middle, __last, __len1, __len2, __comp);
2548*38fd1498Szrj       else
2549*38fd1498Szrj 	std::__merge_adaptive
2550*38fd1498Szrj 	  (__first, __middle, __last, __len1, __len2, __buf.begin(),
2551*38fd1498Szrj 	   _DistanceType(__buf.size()), __comp);
2552*38fd1498Szrj     }
2553*38fd1498Szrj 
2554*38fd1498Szrj   /**
2555*38fd1498Szrj    *  @brief Merges two sorted ranges in place.
2556*38fd1498Szrj    *  @ingroup sorting_algorithms
2557*38fd1498Szrj    *  @param  __first   An iterator.
2558*38fd1498Szrj    *  @param  __middle  Another iterator.
2559*38fd1498Szrj    *  @param  __last    Another iterator.
2560*38fd1498Szrj    *  @return  Nothing.
2561*38fd1498Szrj    *
2562*38fd1498Szrj    *  Merges two sorted and consecutive ranges, [__first,__middle) and
2563*38fd1498Szrj    *  [__middle,__last), and puts the result in [__first,__last).  The
2564*38fd1498Szrj    *  output will be sorted.  The sort is @e stable, that is, for
2565*38fd1498Szrj    *  equivalent elements in the two ranges, elements from the first
2566*38fd1498Szrj    *  range will always come before elements from the second.
2567*38fd1498Szrj    *
2568*38fd1498Szrj    *  If enough additional memory is available, this takes (__last-__first)-1
2569*38fd1498Szrj    *  comparisons.  Otherwise an NlogN algorithm is used, where N is
2570*38fd1498Szrj    *  distance(__first,__last).
2571*38fd1498Szrj   */
2572*38fd1498Szrj   template<typename _BidirectionalIterator>
2573*38fd1498Szrj     inline void
2574*38fd1498Szrj     inplace_merge(_BidirectionalIterator __first,
2575*38fd1498Szrj 		  _BidirectionalIterator __middle,
2576*38fd1498Szrj 		  _BidirectionalIterator __last)
2577*38fd1498Szrj     {
2578*38fd1498Szrj       // concept requirements
2579*38fd1498Szrj       __glibcxx_function_requires(_Mutable_BidirectionalIteratorConcept<
2580*38fd1498Szrj 	    _BidirectionalIterator>)
2581*38fd1498Szrj       __glibcxx_function_requires(_LessThanComparableConcept<
2582*38fd1498Szrj 	    typename iterator_traits<_BidirectionalIterator>::value_type>)
2583*38fd1498Szrj       __glibcxx_requires_sorted(__first, __middle);
2584*38fd1498Szrj       __glibcxx_requires_sorted(__middle, __last);
2585*38fd1498Szrj       __glibcxx_requires_irreflexive(__first, __last);
2586*38fd1498Szrj 
2587*38fd1498Szrj       std::__inplace_merge(__first, __middle, __last,
2588*38fd1498Szrj 			   __gnu_cxx::__ops::__iter_less_iter());
2589*38fd1498Szrj     }
2590*38fd1498Szrj 
2591*38fd1498Szrj   /**
2592*38fd1498Szrj    *  @brief Merges two sorted ranges in place.
2593*38fd1498Szrj    *  @ingroup sorting_algorithms
2594*38fd1498Szrj    *  @param  __first   An iterator.
2595*38fd1498Szrj    *  @param  __middle  Another iterator.
2596*38fd1498Szrj    *  @param  __last    Another iterator.
2597*38fd1498Szrj    *  @param  __comp    A functor to use for comparisons.
2598*38fd1498Szrj    *  @return  Nothing.
2599*38fd1498Szrj    *
2600*38fd1498Szrj    *  Merges two sorted and consecutive ranges, [__first,__middle) and
2601*38fd1498Szrj    *  [middle,last), and puts the result in [__first,__last).  The output will
2602*38fd1498Szrj    *  be sorted.  The sort is @e stable, that is, for equivalent
2603*38fd1498Szrj    *  elements in the two ranges, elements from the first range will always
2604*38fd1498Szrj    *  come before elements from the second.
2605*38fd1498Szrj    *
2606*38fd1498Szrj    *  If enough additional memory is available, this takes (__last-__first)-1
2607*38fd1498Szrj    *  comparisons.  Otherwise an NlogN algorithm is used, where N is
2608*38fd1498Szrj    *  distance(__first,__last).
2609*38fd1498Szrj    *
2610*38fd1498Szrj    *  The comparison function should have the same effects on ordering as
2611*38fd1498Szrj    *  the function used for the initial sort.
2612*38fd1498Szrj   */
2613*38fd1498Szrj   template<typename _BidirectionalIterator, typename _Compare>
2614*38fd1498Szrj     inline void
2615*38fd1498Szrj     inplace_merge(_BidirectionalIterator __first,
2616*38fd1498Szrj 		  _BidirectionalIterator __middle,
2617*38fd1498Szrj 		  _BidirectionalIterator __last,
2618*38fd1498Szrj 		  _Compare __comp)
2619*38fd1498Szrj     {
2620*38fd1498Szrj       // concept requirements
2621*38fd1498Szrj       __glibcxx_function_requires(_Mutable_BidirectionalIteratorConcept<
2622*38fd1498Szrj 	    _BidirectionalIterator>)
2623*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
2624*38fd1498Szrj 	    typename iterator_traits<_BidirectionalIterator>::value_type,
2625*38fd1498Szrj 	    typename iterator_traits<_BidirectionalIterator>::value_type>)
2626*38fd1498Szrj       __glibcxx_requires_sorted_pred(__first, __middle, __comp);
2627*38fd1498Szrj       __glibcxx_requires_sorted_pred(__middle, __last, __comp);
2628*38fd1498Szrj       __glibcxx_requires_irreflexive_pred(__first, __last, __comp);
2629*38fd1498Szrj 
2630*38fd1498Szrj       std::__inplace_merge(__first, __middle, __last,
2631*38fd1498Szrj 			   __gnu_cxx::__ops::__iter_comp_iter(__comp));
2632*38fd1498Szrj     }
2633*38fd1498Szrj 
2634*38fd1498Szrj 
2635*38fd1498Szrj   /// This is a helper function for the __merge_sort_loop routines.
2636*38fd1498Szrj   template<typename _InputIterator, typename _OutputIterator,
2637*38fd1498Szrj 	   typename _Compare>
2638*38fd1498Szrj     _OutputIterator
2639*38fd1498Szrj     __move_merge(_InputIterator __first1, _InputIterator __last1,
2640*38fd1498Szrj 		 _InputIterator __first2, _InputIterator __last2,
2641*38fd1498Szrj 		 _OutputIterator __result, _Compare __comp)
2642*38fd1498Szrj     {
2643*38fd1498Szrj       while (__first1 != __last1 && __first2 != __last2)
2644*38fd1498Szrj 	{
2645*38fd1498Szrj 	  if (__comp(__first2, __first1))
2646*38fd1498Szrj 	    {
2647*38fd1498Szrj 	      *__result = _GLIBCXX_MOVE(*__first2);
2648*38fd1498Szrj 	      ++__first2;
2649*38fd1498Szrj 	    }
2650*38fd1498Szrj 	  else
2651*38fd1498Szrj 	    {
2652*38fd1498Szrj 	      *__result = _GLIBCXX_MOVE(*__first1);
2653*38fd1498Szrj 	      ++__first1;
2654*38fd1498Szrj 	    }
2655*38fd1498Szrj 	  ++__result;
2656*38fd1498Szrj 	}
2657*38fd1498Szrj       return _GLIBCXX_MOVE3(__first2, __last2,
2658*38fd1498Szrj 			    _GLIBCXX_MOVE3(__first1, __last1,
2659*38fd1498Szrj 					   __result));
2660*38fd1498Szrj     }
2661*38fd1498Szrj 
2662*38fd1498Szrj   template<typename _RandomAccessIterator1, typename _RandomAccessIterator2,
2663*38fd1498Szrj 	   typename _Distance, typename _Compare>
2664*38fd1498Szrj     void
2665*38fd1498Szrj     __merge_sort_loop(_RandomAccessIterator1 __first,
2666*38fd1498Szrj 		      _RandomAccessIterator1 __last,
2667*38fd1498Szrj 		      _RandomAccessIterator2 __result, _Distance __step_size,
2668*38fd1498Szrj 		      _Compare __comp)
2669*38fd1498Szrj     {
2670*38fd1498Szrj       const _Distance __two_step = 2 * __step_size;
2671*38fd1498Szrj 
2672*38fd1498Szrj       while (__last - __first >= __two_step)
2673*38fd1498Szrj 	{
2674*38fd1498Szrj 	  __result = std::__move_merge(__first, __first + __step_size,
2675*38fd1498Szrj 				       __first + __step_size,
2676*38fd1498Szrj 				       __first + __two_step,
2677*38fd1498Szrj 				       __result, __comp);
2678*38fd1498Szrj 	  __first += __two_step;
2679*38fd1498Szrj 	}
2680*38fd1498Szrj       __step_size = std::min(_Distance(__last - __first), __step_size);
2681*38fd1498Szrj 
2682*38fd1498Szrj       std::__move_merge(__first, __first + __step_size,
2683*38fd1498Szrj 			__first + __step_size, __last, __result, __comp);
2684*38fd1498Szrj     }
2685*38fd1498Szrj 
2686*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Distance,
2687*38fd1498Szrj 	   typename _Compare>
2688*38fd1498Szrj     void
2689*38fd1498Szrj     __chunk_insertion_sort(_RandomAccessIterator __first,
2690*38fd1498Szrj 			   _RandomAccessIterator __last,
2691*38fd1498Szrj 			   _Distance __chunk_size, _Compare __comp)
2692*38fd1498Szrj     {
2693*38fd1498Szrj       while (__last - __first >= __chunk_size)
2694*38fd1498Szrj 	{
2695*38fd1498Szrj 	  std::__insertion_sort(__first, __first + __chunk_size, __comp);
2696*38fd1498Szrj 	  __first += __chunk_size;
2697*38fd1498Szrj 	}
2698*38fd1498Szrj       std::__insertion_sort(__first, __last, __comp);
2699*38fd1498Szrj     }
2700*38fd1498Szrj 
2701*38fd1498Szrj   enum { _S_chunk_size = 7 };
2702*38fd1498Szrj 
2703*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Pointer, typename _Compare>
2704*38fd1498Szrj     void
2705*38fd1498Szrj     __merge_sort_with_buffer(_RandomAccessIterator __first,
2706*38fd1498Szrj 			     _RandomAccessIterator __last,
2707*38fd1498Szrj 			     _Pointer __buffer, _Compare __comp)
2708*38fd1498Szrj     {
2709*38fd1498Szrj       typedef typename iterator_traits<_RandomAccessIterator>::difference_type
2710*38fd1498Szrj 	_Distance;
2711*38fd1498Szrj 
2712*38fd1498Szrj       const _Distance __len = __last - __first;
2713*38fd1498Szrj       const _Pointer __buffer_last = __buffer + __len;
2714*38fd1498Szrj 
2715*38fd1498Szrj       _Distance __step_size = _S_chunk_size;
2716*38fd1498Szrj       std::__chunk_insertion_sort(__first, __last, __step_size, __comp);
2717*38fd1498Szrj 
2718*38fd1498Szrj       while (__step_size < __len)
2719*38fd1498Szrj 	{
2720*38fd1498Szrj 	  std::__merge_sort_loop(__first, __last, __buffer,
2721*38fd1498Szrj 				 __step_size, __comp);
2722*38fd1498Szrj 	  __step_size *= 2;
2723*38fd1498Szrj 	  std::__merge_sort_loop(__buffer, __buffer_last, __first,
2724*38fd1498Szrj 				 __step_size, __comp);
2725*38fd1498Szrj 	  __step_size *= 2;
2726*38fd1498Szrj 	}
2727*38fd1498Szrj     }
2728*38fd1498Szrj 
2729*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Pointer,
2730*38fd1498Szrj 	   typename _Distance, typename _Compare>
2731*38fd1498Szrj     void
2732*38fd1498Szrj     __stable_sort_adaptive(_RandomAccessIterator __first,
2733*38fd1498Szrj 			   _RandomAccessIterator __last,
2734*38fd1498Szrj 			   _Pointer __buffer, _Distance __buffer_size,
2735*38fd1498Szrj 			   _Compare __comp)
2736*38fd1498Szrj     {
2737*38fd1498Szrj       const _Distance __len = (__last - __first + 1) / 2;
2738*38fd1498Szrj       const _RandomAccessIterator __middle = __first + __len;
2739*38fd1498Szrj       if (__len > __buffer_size)
2740*38fd1498Szrj 	{
2741*38fd1498Szrj 	  std::__stable_sort_adaptive(__first, __middle, __buffer,
2742*38fd1498Szrj 				      __buffer_size, __comp);
2743*38fd1498Szrj 	  std::__stable_sort_adaptive(__middle, __last, __buffer,
2744*38fd1498Szrj 				      __buffer_size, __comp);
2745*38fd1498Szrj 	}
2746*38fd1498Szrj       else
2747*38fd1498Szrj 	{
2748*38fd1498Szrj 	  std::__merge_sort_with_buffer(__first, __middle, __buffer, __comp);
2749*38fd1498Szrj 	  std::__merge_sort_with_buffer(__middle, __last, __buffer, __comp);
2750*38fd1498Szrj 	}
2751*38fd1498Szrj       std::__merge_adaptive(__first, __middle, __last,
2752*38fd1498Szrj 			    _Distance(__middle - __first),
2753*38fd1498Szrj 			    _Distance(__last - __middle),
2754*38fd1498Szrj 			    __buffer, __buffer_size,
2755*38fd1498Szrj 			    __comp);
2756*38fd1498Szrj     }
2757*38fd1498Szrj 
2758*38fd1498Szrj   /// This is a helper function for the stable sorting routines.
2759*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
2760*38fd1498Szrj     void
2761*38fd1498Szrj     __inplace_stable_sort(_RandomAccessIterator __first,
2762*38fd1498Szrj 			  _RandomAccessIterator __last, _Compare __comp)
2763*38fd1498Szrj     {
2764*38fd1498Szrj       if (__last - __first < 15)
2765*38fd1498Szrj 	{
2766*38fd1498Szrj 	  std::__insertion_sort(__first, __last, __comp);
2767*38fd1498Szrj 	  return;
2768*38fd1498Szrj 	}
2769*38fd1498Szrj       _RandomAccessIterator __middle = __first + (__last - __first) / 2;
2770*38fd1498Szrj       std::__inplace_stable_sort(__first, __middle, __comp);
2771*38fd1498Szrj       std::__inplace_stable_sort(__middle, __last, __comp);
2772*38fd1498Szrj       std::__merge_without_buffer(__first, __middle, __last,
2773*38fd1498Szrj 				  __middle - __first,
2774*38fd1498Szrj 				  __last - __middle,
2775*38fd1498Szrj 				  __comp);
2776*38fd1498Szrj     }
2777*38fd1498Szrj 
2778*38fd1498Szrj   // stable_sort
2779*38fd1498Szrj 
2780*38fd1498Szrj   // Set algorithms: includes, set_union, set_intersection, set_difference,
2781*38fd1498Szrj   // set_symmetric_difference.  All of these algorithms have the precondition
2782*38fd1498Szrj   // that their input ranges are sorted and the postcondition that their output
2783*38fd1498Szrj   // ranges are sorted.
2784*38fd1498Szrj 
2785*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
2786*38fd1498Szrj 	   typename _Compare>
2787*38fd1498Szrj     bool
2788*38fd1498Szrj     __includes(_InputIterator1 __first1, _InputIterator1 __last1,
2789*38fd1498Szrj 	       _InputIterator2 __first2, _InputIterator2 __last2,
2790*38fd1498Szrj 	       _Compare __comp)
2791*38fd1498Szrj     {
2792*38fd1498Szrj       while (__first1 != __last1 && __first2 != __last2)
2793*38fd1498Szrj 	if (__comp(__first2, __first1))
2794*38fd1498Szrj 	  return false;
2795*38fd1498Szrj 	else if (__comp(__first1, __first2))
2796*38fd1498Szrj 	  ++__first1;
2797*38fd1498Szrj 	else
2798*38fd1498Szrj 	  {
2799*38fd1498Szrj 	    ++__first1;
2800*38fd1498Szrj 	    ++__first2;
2801*38fd1498Szrj 	  }
2802*38fd1498Szrj 
2803*38fd1498Szrj       return __first2 == __last2;
2804*38fd1498Szrj     }
2805*38fd1498Szrj 
2806*38fd1498Szrj   /**
2807*38fd1498Szrj    *  @brief Determines whether all elements of a sequence exists in a range.
2808*38fd1498Szrj    *  @param  __first1  Start of search range.
2809*38fd1498Szrj    *  @param  __last1   End of search range.
2810*38fd1498Szrj    *  @param  __first2  Start of sequence
2811*38fd1498Szrj    *  @param  __last2   End of sequence.
2812*38fd1498Szrj    *  @return  True if each element in [__first2,__last2) is contained in order
2813*38fd1498Szrj    *  within [__first1,__last1).  False otherwise.
2814*38fd1498Szrj    *  @ingroup set_algorithms
2815*38fd1498Szrj    *
2816*38fd1498Szrj    *  This operation expects both [__first1,__last1) and
2817*38fd1498Szrj    *  [__first2,__last2) to be sorted.  Searches for the presence of
2818*38fd1498Szrj    *  each element in [__first2,__last2) within [__first1,__last1).
2819*38fd1498Szrj    *  The iterators over each range only move forward, so this is a
2820*38fd1498Szrj    *  linear algorithm.  If an element in [__first2,__last2) is not
2821*38fd1498Szrj    *  found before the search iterator reaches @p __last2, false is
2822*38fd1498Szrj    *  returned.
2823*38fd1498Szrj   */
2824*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2>
2825*38fd1498Szrj     inline bool
2826*38fd1498Szrj     includes(_InputIterator1 __first1, _InputIterator1 __last1,
2827*38fd1498Szrj 	     _InputIterator2 __first2, _InputIterator2 __last2)
2828*38fd1498Szrj     {
2829*38fd1498Szrj       // concept requirements
2830*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator1>)
2831*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator2>)
2832*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
2833*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type,
2834*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
2835*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
2836*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type,
2837*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
2838*38fd1498Szrj       __glibcxx_requires_sorted_set(__first1, __last1, __first2);
2839*38fd1498Szrj       __glibcxx_requires_sorted_set(__first2, __last2, __first1);
2840*38fd1498Szrj       __glibcxx_requires_irreflexive2(__first1, __last1);
2841*38fd1498Szrj       __glibcxx_requires_irreflexive2(__first2, __last2);
2842*38fd1498Szrj 
2843*38fd1498Szrj       return std::__includes(__first1, __last1, __first2, __last2,
2844*38fd1498Szrj 			     __gnu_cxx::__ops::__iter_less_iter());
2845*38fd1498Szrj     }
2846*38fd1498Szrj 
2847*38fd1498Szrj   /**
2848*38fd1498Szrj    *  @brief Determines whether all elements of a sequence exists in a range
2849*38fd1498Szrj    *  using comparison.
2850*38fd1498Szrj    *  @ingroup set_algorithms
2851*38fd1498Szrj    *  @param  __first1  Start of search range.
2852*38fd1498Szrj    *  @param  __last1   End of search range.
2853*38fd1498Szrj    *  @param  __first2  Start of sequence
2854*38fd1498Szrj    *  @param  __last2   End of sequence.
2855*38fd1498Szrj    *  @param  __comp    Comparison function to use.
2856*38fd1498Szrj    *  @return True if each element in [__first2,__last2) is contained
2857*38fd1498Szrj    *  in order within [__first1,__last1) according to comp.  False
2858*38fd1498Szrj    *  otherwise.  @ingroup set_algorithms
2859*38fd1498Szrj    *
2860*38fd1498Szrj    *  This operation expects both [__first1,__last1) and
2861*38fd1498Szrj    *  [__first2,__last2) to be sorted.  Searches for the presence of
2862*38fd1498Szrj    *  each element in [__first2,__last2) within [__first1,__last1),
2863*38fd1498Szrj    *  using comp to decide.  The iterators over each range only move
2864*38fd1498Szrj    *  forward, so this is a linear algorithm.  If an element in
2865*38fd1498Szrj    *  [__first2,__last2) is not found before the search iterator
2866*38fd1498Szrj    *  reaches @p __last2, false is returned.
2867*38fd1498Szrj   */
2868*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
2869*38fd1498Szrj 	   typename _Compare>
2870*38fd1498Szrj     inline bool
2871*38fd1498Szrj     includes(_InputIterator1 __first1, _InputIterator1 __last1,
2872*38fd1498Szrj 	     _InputIterator2 __first2, _InputIterator2 __last2,
2873*38fd1498Szrj 	     _Compare __comp)
2874*38fd1498Szrj     {
2875*38fd1498Szrj       // concept requirements
2876*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator1>)
2877*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator2>)
2878*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
2879*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type,
2880*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
2881*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
2882*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type,
2883*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
2884*38fd1498Szrj       __glibcxx_requires_sorted_set_pred(__first1, __last1, __first2, __comp);
2885*38fd1498Szrj       __glibcxx_requires_sorted_set_pred(__first2, __last2, __first1, __comp);
2886*38fd1498Szrj       __glibcxx_requires_irreflexive_pred2(__first1, __last1, __comp);
2887*38fd1498Szrj       __glibcxx_requires_irreflexive_pred2(__first2, __last2, __comp);
2888*38fd1498Szrj 
2889*38fd1498Szrj       return std::__includes(__first1, __last1, __first2, __last2,
2890*38fd1498Szrj 			     __gnu_cxx::__ops::__iter_comp_iter(__comp));
2891*38fd1498Szrj     }
2892*38fd1498Szrj 
2893*38fd1498Szrj   // nth_element
2894*38fd1498Szrj   // merge
2895*38fd1498Szrj   // set_difference
2896*38fd1498Szrj   // set_intersection
2897*38fd1498Szrj   // set_union
2898*38fd1498Szrj   // stable_sort
2899*38fd1498Szrj   // set_symmetric_difference
2900*38fd1498Szrj   // min_element
2901*38fd1498Szrj   // max_element
2902*38fd1498Szrj 
2903*38fd1498Szrj   template<typename _BidirectionalIterator, typename _Compare>
2904*38fd1498Szrj     bool
2905*38fd1498Szrj     __next_permutation(_BidirectionalIterator __first,
2906*38fd1498Szrj 		       _BidirectionalIterator __last, _Compare __comp)
2907*38fd1498Szrj     {
2908*38fd1498Szrj       if (__first == __last)
2909*38fd1498Szrj 	return false;
2910*38fd1498Szrj       _BidirectionalIterator __i = __first;
2911*38fd1498Szrj       ++__i;
2912*38fd1498Szrj       if (__i == __last)
2913*38fd1498Szrj 	return false;
2914*38fd1498Szrj       __i = __last;
2915*38fd1498Szrj       --__i;
2916*38fd1498Szrj 
2917*38fd1498Szrj       for(;;)
2918*38fd1498Szrj 	{
2919*38fd1498Szrj 	  _BidirectionalIterator __ii = __i;
2920*38fd1498Szrj 	  --__i;
2921*38fd1498Szrj 	  if (__comp(__i, __ii))
2922*38fd1498Szrj 	    {
2923*38fd1498Szrj 	      _BidirectionalIterator __j = __last;
2924*38fd1498Szrj 	      while (!__comp(__i, --__j))
2925*38fd1498Szrj 		{}
2926*38fd1498Szrj 	      std::iter_swap(__i, __j);
2927*38fd1498Szrj 	      std::__reverse(__ii, __last,
2928*38fd1498Szrj 			     std::__iterator_category(__first));
2929*38fd1498Szrj 	      return true;
2930*38fd1498Szrj 	    }
2931*38fd1498Szrj 	  if (__i == __first)
2932*38fd1498Szrj 	    {
2933*38fd1498Szrj 	      std::__reverse(__first, __last,
2934*38fd1498Szrj 			     std::__iterator_category(__first));
2935*38fd1498Szrj 	      return false;
2936*38fd1498Szrj 	    }
2937*38fd1498Szrj 	}
2938*38fd1498Szrj     }
2939*38fd1498Szrj 
2940*38fd1498Szrj   /**
2941*38fd1498Szrj    *  @brief  Permute range into the next @e dictionary ordering.
2942*38fd1498Szrj    *  @ingroup sorting_algorithms
2943*38fd1498Szrj    *  @param  __first  Start of range.
2944*38fd1498Szrj    *  @param  __last   End of range.
2945*38fd1498Szrj    *  @return  False if wrapped to first permutation, true otherwise.
2946*38fd1498Szrj    *
2947*38fd1498Szrj    *  Treats all permutations of the range as a set of @e dictionary sorted
2948*38fd1498Szrj    *  sequences.  Permutes the current sequence into the next one of this set.
2949*38fd1498Szrj    *  Returns true if there are more sequences to generate.  If the sequence
2950*38fd1498Szrj    *  is the largest of the set, the smallest is generated and false returned.
2951*38fd1498Szrj   */
2952*38fd1498Szrj   template<typename _BidirectionalIterator>
2953*38fd1498Szrj     inline bool
2954*38fd1498Szrj     next_permutation(_BidirectionalIterator __first,
2955*38fd1498Szrj 		     _BidirectionalIterator __last)
2956*38fd1498Szrj     {
2957*38fd1498Szrj       // concept requirements
2958*38fd1498Szrj       __glibcxx_function_requires(_BidirectionalIteratorConcept<
2959*38fd1498Szrj 				  _BidirectionalIterator>)
2960*38fd1498Szrj       __glibcxx_function_requires(_LessThanComparableConcept<
2961*38fd1498Szrj 	    typename iterator_traits<_BidirectionalIterator>::value_type>)
2962*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
2963*38fd1498Szrj       __glibcxx_requires_irreflexive(__first, __last);
2964*38fd1498Szrj 
2965*38fd1498Szrj       return std::__next_permutation
2966*38fd1498Szrj 	(__first, __last, __gnu_cxx::__ops::__iter_less_iter());
2967*38fd1498Szrj     }
2968*38fd1498Szrj 
2969*38fd1498Szrj   /**
2970*38fd1498Szrj    *  @brief  Permute range into the next @e dictionary ordering using
2971*38fd1498Szrj    *          comparison functor.
2972*38fd1498Szrj    *  @ingroup sorting_algorithms
2973*38fd1498Szrj    *  @param  __first  Start of range.
2974*38fd1498Szrj    *  @param  __last   End of range.
2975*38fd1498Szrj    *  @param  __comp   A comparison functor.
2976*38fd1498Szrj    *  @return  False if wrapped to first permutation, true otherwise.
2977*38fd1498Szrj    *
2978*38fd1498Szrj    *  Treats all permutations of the range [__first,__last) as a set of
2979*38fd1498Szrj    *  @e dictionary sorted sequences ordered by @p __comp.  Permutes the current
2980*38fd1498Szrj    *  sequence into the next one of this set.  Returns true if there are more
2981*38fd1498Szrj    *  sequences to generate.  If the sequence is the largest of the set, the
2982*38fd1498Szrj    *  smallest is generated and false returned.
2983*38fd1498Szrj   */
2984*38fd1498Szrj   template<typename _BidirectionalIterator, typename _Compare>
2985*38fd1498Szrj     inline bool
2986*38fd1498Szrj     next_permutation(_BidirectionalIterator __first,
2987*38fd1498Szrj 		     _BidirectionalIterator __last, _Compare __comp)
2988*38fd1498Szrj     {
2989*38fd1498Szrj       // concept requirements
2990*38fd1498Szrj       __glibcxx_function_requires(_BidirectionalIteratorConcept<
2991*38fd1498Szrj 				  _BidirectionalIterator>)
2992*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
2993*38fd1498Szrj 	    typename iterator_traits<_BidirectionalIterator>::value_type,
2994*38fd1498Szrj 	    typename iterator_traits<_BidirectionalIterator>::value_type>)
2995*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
2996*38fd1498Szrj       __glibcxx_requires_irreflexive_pred(__first, __last, __comp);
2997*38fd1498Szrj 
2998*38fd1498Szrj       return std::__next_permutation
2999*38fd1498Szrj 	(__first, __last, __gnu_cxx::__ops::__iter_comp_iter(__comp));
3000*38fd1498Szrj     }
3001*38fd1498Szrj 
3002*38fd1498Szrj   template<typename _BidirectionalIterator, typename _Compare>
3003*38fd1498Szrj     bool
3004*38fd1498Szrj     __prev_permutation(_BidirectionalIterator __first,
3005*38fd1498Szrj 		       _BidirectionalIterator __last, _Compare __comp)
3006*38fd1498Szrj     {
3007*38fd1498Szrj       if (__first == __last)
3008*38fd1498Szrj 	return false;
3009*38fd1498Szrj       _BidirectionalIterator __i = __first;
3010*38fd1498Szrj       ++__i;
3011*38fd1498Szrj       if (__i == __last)
3012*38fd1498Szrj 	return false;
3013*38fd1498Szrj       __i = __last;
3014*38fd1498Szrj       --__i;
3015*38fd1498Szrj 
3016*38fd1498Szrj       for(;;)
3017*38fd1498Szrj 	{
3018*38fd1498Szrj 	  _BidirectionalIterator __ii = __i;
3019*38fd1498Szrj 	  --__i;
3020*38fd1498Szrj 	  if (__comp(__ii, __i))
3021*38fd1498Szrj 	    {
3022*38fd1498Szrj 	      _BidirectionalIterator __j = __last;
3023*38fd1498Szrj 	      while (!__comp(--__j, __i))
3024*38fd1498Szrj 		{}
3025*38fd1498Szrj 	      std::iter_swap(__i, __j);
3026*38fd1498Szrj 	      std::__reverse(__ii, __last,
3027*38fd1498Szrj 			     std::__iterator_category(__first));
3028*38fd1498Szrj 	      return true;
3029*38fd1498Szrj 	    }
3030*38fd1498Szrj 	  if (__i == __first)
3031*38fd1498Szrj 	    {
3032*38fd1498Szrj 	      std::__reverse(__first, __last,
3033*38fd1498Szrj 			     std::__iterator_category(__first));
3034*38fd1498Szrj 	      return false;
3035*38fd1498Szrj 	    }
3036*38fd1498Szrj 	}
3037*38fd1498Szrj     }
3038*38fd1498Szrj 
3039*38fd1498Szrj   /**
3040*38fd1498Szrj    *  @brief  Permute range into the previous @e dictionary ordering.
3041*38fd1498Szrj    *  @ingroup sorting_algorithms
3042*38fd1498Szrj    *  @param  __first  Start of range.
3043*38fd1498Szrj    *  @param  __last   End of range.
3044*38fd1498Szrj    *  @return  False if wrapped to last permutation, true otherwise.
3045*38fd1498Szrj    *
3046*38fd1498Szrj    *  Treats all permutations of the range as a set of @e dictionary sorted
3047*38fd1498Szrj    *  sequences.  Permutes the current sequence into the previous one of this
3048*38fd1498Szrj    *  set.  Returns true if there are more sequences to generate.  If the
3049*38fd1498Szrj    *  sequence is the smallest of the set, the largest is generated and false
3050*38fd1498Szrj    *  returned.
3051*38fd1498Szrj   */
3052*38fd1498Szrj   template<typename _BidirectionalIterator>
3053*38fd1498Szrj     inline bool
3054*38fd1498Szrj     prev_permutation(_BidirectionalIterator __first,
3055*38fd1498Szrj 		     _BidirectionalIterator __last)
3056*38fd1498Szrj     {
3057*38fd1498Szrj       // concept requirements
3058*38fd1498Szrj       __glibcxx_function_requires(_BidirectionalIteratorConcept<
3059*38fd1498Szrj 				  _BidirectionalIterator>)
3060*38fd1498Szrj       __glibcxx_function_requires(_LessThanComparableConcept<
3061*38fd1498Szrj 	    typename iterator_traits<_BidirectionalIterator>::value_type>)
3062*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
3063*38fd1498Szrj       __glibcxx_requires_irreflexive(__first, __last);
3064*38fd1498Szrj 
3065*38fd1498Szrj       return std::__prev_permutation(__first, __last,
3066*38fd1498Szrj 				     __gnu_cxx::__ops::__iter_less_iter());
3067*38fd1498Szrj     }
3068*38fd1498Szrj 
3069*38fd1498Szrj   /**
3070*38fd1498Szrj    *  @brief  Permute range into the previous @e dictionary ordering using
3071*38fd1498Szrj    *          comparison functor.
3072*38fd1498Szrj    *  @ingroup sorting_algorithms
3073*38fd1498Szrj    *  @param  __first  Start of range.
3074*38fd1498Szrj    *  @param  __last   End of range.
3075*38fd1498Szrj    *  @param  __comp   A comparison functor.
3076*38fd1498Szrj    *  @return  False if wrapped to last permutation, true otherwise.
3077*38fd1498Szrj    *
3078*38fd1498Szrj    *  Treats all permutations of the range [__first,__last) as a set of
3079*38fd1498Szrj    *  @e dictionary sorted sequences ordered by @p __comp.  Permutes the current
3080*38fd1498Szrj    *  sequence into the previous one of this set.  Returns true if there are
3081*38fd1498Szrj    *  more sequences to generate.  If the sequence is the smallest of the set,
3082*38fd1498Szrj    *  the largest is generated and false returned.
3083*38fd1498Szrj   */
3084*38fd1498Szrj   template<typename _BidirectionalIterator, typename _Compare>
3085*38fd1498Szrj     inline bool
3086*38fd1498Szrj     prev_permutation(_BidirectionalIterator __first,
3087*38fd1498Szrj 		     _BidirectionalIterator __last, _Compare __comp)
3088*38fd1498Szrj     {
3089*38fd1498Szrj       // concept requirements
3090*38fd1498Szrj       __glibcxx_function_requires(_BidirectionalIteratorConcept<
3091*38fd1498Szrj 				  _BidirectionalIterator>)
3092*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
3093*38fd1498Szrj 	    typename iterator_traits<_BidirectionalIterator>::value_type,
3094*38fd1498Szrj 	    typename iterator_traits<_BidirectionalIterator>::value_type>)
3095*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
3096*38fd1498Szrj       __glibcxx_requires_irreflexive_pred(__first, __last, __comp);
3097*38fd1498Szrj 
3098*38fd1498Szrj       return std::__prev_permutation(__first, __last,
3099*38fd1498Szrj 				__gnu_cxx::__ops::__iter_comp_iter(__comp));
3100*38fd1498Szrj     }
3101*38fd1498Szrj 
3102*38fd1498Szrj   // replace
3103*38fd1498Szrj   // replace_if
3104*38fd1498Szrj 
3105*38fd1498Szrj   template<typename _InputIterator, typename _OutputIterator,
3106*38fd1498Szrj 	   typename _Predicate, typename _Tp>
3107*38fd1498Szrj     _OutputIterator
3108*38fd1498Szrj     __replace_copy_if(_InputIterator __first, _InputIterator __last,
3109*38fd1498Szrj 		      _OutputIterator __result,
3110*38fd1498Szrj 		      _Predicate __pred, const _Tp& __new_value)
3111*38fd1498Szrj     {
3112*38fd1498Szrj       for (; __first != __last; ++__first, (void)++__result)
3113*38fd1498Szrj 	if (__pred(__first))
3114*38fd1498Szrj 	  *__result = __new_value;
3115*38fd1498Szrj 	else
3116*38fd1498Szrj 	  *__result = *__first;
3117*38fd1498Szrj       return __result;
3118*38fd1498Szrj     }
3119*38fd1498Szrj 
3120*38fd1498Szrj   /**
3121*38fd1498Szrj    *  @brief Copy a sequence, replacing each element of one value with another
3122*38fd1498Szrj    *         value.
3123*38fd1498Szrj    *  @param  __first      An input iterator.
3124*38fd1498Szrj    *  @param  __last       An input iterator.
3125*38fd1498Szrj    *  @param  __result     An output iterator.
3126*38fd1498Szrj    *  @param  __old_value  The value to be replaced.
3127*38fd1498Szrj    *  @param  __new_value  The replacement value.
3128*38fd1498Szrj    *  @return   The end of the output sequence, @p result+(last-first).
3129*38fd1498Szrj    *
3130*38fd1498Szrj    *  Copies each element in the input range @p [__first,__last) to the
3131*38fd1498Szrj    *  output range @p [__result,__result+(__last-__first)) replacing elements
3132*38fd1498Szrj    *  equal to @p __old_value with @p __new_value.
3133*38fd1498Szrj   */
3134*38fd1498Szrj   template<typename _InputIterator, typename _OutputIterator, typename _Tp>
3135*38fd1498Szrj     inline _OutputIterator
3136*38fd1498Szrj     replace_copy(_InputIterator __first, _InputIterator __last,
3137*38fd1498Szrj 		 _OutputIterator __result,
3138*38fd1498Szrj 		 const _Tp& __old_value, const _Tp& __new_value)
3139*38fd1498Szrj     {
3140*38fd1498Szrj       // concept requirements
3141*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
3142*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
3143*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
3144*38fd1498Szrj       __glibcxx_function_requires(_EqualOpConcept<
3145*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type, _Tp>)
3146*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
3147*38fd1498Szrj 
3148*38fd1498Szrj       return std::__replace_copy_if(__first, __last, __result,
3149*38fd1498Szrj 			__gnu_cxx::__ops::__iter_equals_val(__old_value),
3150*38fd1498Szrj 					      __new_value);
3151*38fd1498Szrj     }
3152*38fd1498Szrj 
3153*38fd1498Szrj   /**
3154*38fd1498Szrj    *  @brief Copy a sequence, replacing each value for which a predicate
3155*38fd1498Szrj    *         returns true with another value.
3156*38fd1498Szrj    *  @ingroup mutating_algorithms
3157*38fd1498Szrj    *  @param  __first      An input iterator.
3158*38fd1498Szrj    *  @param  __last       An input iterator.
3159*38fd1498Szrj    *  @param  __result     An output iterator.
3160*38fd1498Szrj    *  @param  __pred       A predicate.
3161*38fd1498Szrj    *  @param  __new_value  The replacement value.
3162*38fd1498Szrj    *  @return   The end of the output sequence, @p __result+(__last-__first).
3163*38fd1498Szrj    *
3164*38fd1498Szrj    *  Copies each element in the range @p [__first,__last) to the range
3165*38fd1498Szrj    *  @p [__result,__result+(__last-__first)) replacing elements for which
3166*38fd1498Szrj    *  @p __pred returns true with @p __new_value.
3167*38fd1498Szrj   */
3168*38fd1498Szrj   template<typename _InputIterator, typename _OutputIterator,
3169*38fd1498Szrj 	   typename _Predicate, typename _Tp>
3170*38fd1498Szrj     inline _OutputIterator
3171*38fd1498Szrj     replace_copy_if(_InputIterator __first, _InputIterator __last,
3172*38fd1498Szrj 		    _OutputIterator __result,
3173*38fd1498Szrj 		    _Predicate __pred, const _Tp& __new_value)
3174*38fd1498Szrj     {
3175*38fd1498Szrj       // concept requirements
3176*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
3177*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
3178*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
3179*38fd1498Szrj       __glibcxx_function_requires(_UnaryPredicateConcept<_Predicate,
3180*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
3181*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
3182*38fd1498Szrj 
3183*38fd1498Szrj       return std::__replace_copy_if(__first, __last, __result,
3184*38fd1498Szrj 				__gnu_cxx::__ops::__pred_iter(__pred),
3185*38fd1498Szrj 					      __new_value);
3186*38fd1498Szrj     }
3187*38fd1498Szrj 
3188*38fd1498Szrj   template<typename _InputIterator, typename _Predicate>
3189*38fd1498Szrj     typename iterator_traits<_InputIterator>::difference_type
3190*38fd1498Szrj     __count_if(_InputIterator __first, _InputIterator __last, _Predicate __pred)
3191*38fd1498Szrj     {
3192*38fd1498Szrj       typename iterator_traits<_InputIterator>::difference_type __n = 0;
3193*38fd1498Szrj       for (; __first != __last; ++__first)
3194*38fd1498Szrj 	if (__pred(__first))
3195*38fd1498Szrj 	  ++__n;
3196*38fd1498Szrj       return __n;
3197*38fd1498Szrj     }
3198*38fd1498Szrj 
3199*38fd1498Szrj #if __cplusplus >= 201103L
3200*38fd1498Szrj   /**
3201*38fd1498Szrj    *  @brief  Determines whether the elements of a sequence are sorted.
3202*38fd1498Szrj    *  @ingroup sorting_algorithms
3203*38fd1498Szrj    *  @param  __first   An iterator.
3204*38fd1498Szrj    *  @param  __last    Another iterator.
3205*38fd1498Szrj    *  @return  True if the elements are sorted, false otherwise.
3206*38fd1498Szrj   */
3207*38fd1498Szrj   template<typename _ForwardIterator>
3208*38fd1498Szrj     inline bool
3209*38fd1498Szrj     is_sorted(_ForwardIterator __first, _ForwardIterator __last)
3210*38fd1498Szrj     { return std::is_sorted_until(__first, __last) == __last; }
3211*38fd1498Szrj 
3212*38fd1498Szrj   /**
3213*38fd1498Szrj    *  @brief  Determines whether the elements of a sequence are sorted
3214*38fd1498Szrj    *          according to a comparison functor.
3215*38fd1498Szrj    *  @ingroup sorting_algorithms
3216*38fd1498Szrj    *  @param  __first   An iterator.
3217*38fd1498Szrj    *  @param  __last    Another iterator.
3218*38fd1498Szrj    *  @param  __comp    A comparison functor.
3219*38fd1498Szrj    *  @return  True if the elements are sorted, false otherwise.
3220*38fd1498Szrj   */
3221*38fd1498Szrj   template<typename _ForwardIterator, typename _Compare>
3222*38fd1498Szrj     inline bool
3223*38fd1498Szrj     is_sorted(_ForwardIterator __first, _ForwardIterator __last,
3224*38fd1498Szrj 	      _Compare __comp)
3225*38fd1498Szrj     { return std::is_sorted_until(__first, __last, __comp) == __last; }
3226*38fd1498Szrj 
3227*38fd1498Szrj   template<typename _ForwardIterator, typename _Compare>
3228*38fd1498Szrj     _ForwardIterator
3229*38fd1498Szrj     __is_sorted_until(_ForwardIterator __first, _ForwardIterator __last,
3230*38fd1498Szrj 		      _Compare __comp)
3231*38fd1498Szrj     {
3232*38fd1498Szrj       if (__first == __last)
3233*38fd1498Szrj 	return __last;
3234*38fd1498Szrj 
3235*38fd1498Szrj       _ForwardIterator __next = __first;
3236*38fd1498Szrj       for (++__next; __next != __last; __first = __next, (void)++__next)
3237*38fd1498Szrj 	if (__comp(__next, __first))
3238*38fd1498Szrj 	  return __next;
3239*38fd1498Szrj       return __next;
3240*38fd1498Szrj     }
3241*38fd1498Szrj 
3242*38fd1498Szrj   /**
3243*38fd1498Szrj    *  @brief  Determines the end of a sorted sequence.
3244*38fd1498Szrj    *  @ingroup sorting_algorithms
3245*38fd1498Szrj    *  @param  __first   An iterator.
3246*38fd1498Szrj    *  @param  __last    Another iterator.
3247*38fd1498Szrj    *  @return  An iterator pointing to the last iterator i in [__first, __last)
3248*38fd1498Szrj    *           for which the range [__first, i) is sorted.
3249*38fd1498Szrj   */
3250*38fd1498Szrj   template<typename _ForwardIterator>
3251*38fd1498Szrj     inline _ForwardIterator
3252*38fd1498Szrj     is_sorted_until(_ForwardIterator __first, _ForwardIterator __last)
3253*38fd1498Szrj     {
3254*38fd1498Szrj       // concept requirements
3255*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
3256*38fd1498Szrj       __glibcxx_function_requires(_LessThanComparableConcept<
3257*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
3258*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
3259*38fd1498Szrj       __glibcxx_requires_irreflexive(__first, __last);
3260*38fd1498Szrj 
3261*38fd1498Szrj       return std::__is_sorted_until(__first, __last,
3262*38fd1498Szrj 				    __gnu_cxx::__ops::__iter_less_iter());
3263*38fd1498Szrj     }
3264*38fd1498Szrj 
3265*38fd1498Szrj   /**
3266*38fd1498Szrj    *  @brief  Determines the end of a sorted sequence using comparison functor.
3267*38fd1498Szrj    *  @ingroup sorting_algorithms
3268*38fd1498Szrj    *  @param  __first   An iterator.
3269*38fd1498Szrj    *  @param  __last    Another iterator.
3270*38fd1498Szrj    *  @param  __comp    A comparison functor.
3271*38fd1498Szrj    *  @return  An iterator pointing to the last iterator i in [__first, __last)
3272*38fd1498Szrj    *           for which the range [__first, i) is sorted.
3273*38fd1498Szrj   */
3274*38fd1498Szrj   template<typename _ForwardIterator, typename _Compare>
3275*38fd1498Szrj     inline _ForwardIterator
3276*38fd1498Szrj     is_sorted_until(_ForwardIterator __first, _ForwardIterator __last,
3277*38fd1498Szrj 		    _Compare __comp)
3278*38fd1498Szrj     {
3279*38fd1498Szrj       // concept requirements
3280*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
3281*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
3282*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type,
3283*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
3284*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
3285*38fd1498Szrj       __glibcxx_requires_irreflexive_pred(__first, __last, __comp);
3286*38fd1498Szrj 
3287*38fd1498Szrj       return std::__is_sorted_until(__first, __last,
3288*38fd1498Szrj 				    __gnu_cxx::__ops::__iter_comp_iter(__comp));
3289*38fd1498Szrj     }
3290*38fd1498Szrj 
3291*38fd1498Szrj   /**
3292*38fd1498Szrj    *  @brief  Determines min and max at once as an ordered pair.
3293*38fd1498Szrj    *  @ingroup sorting_algorithms
3294*38fd1498Szrj    *  @param  __a  A thing of arbitrary type.
3295*38fd1498Szrj    *  @param  __b  Another thing of arbitrary type.
3296*38fd1498Szrj    *  @return A pair(__b, __a) if __b is smaller than __a, pair(__a,
3297*38fd1498Szrj    *  __b) otherwise.
3298*38fd1498Szrj   */
3299*38fd1498Szrj   template<typename _Tp>
3300*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
3301*38fd1498Szrj     inline pair<const _Tp&, const _Tp&>
3302*38fd1498Szrj     minmax(const _Tp& __a, const _Tp& __b)
3303*38fd1498Szrj     {
3304*38fd1498Szrj       // concept requirements
3305*38fd1498Szrj       __glibcxx_function_requires(_LessThanComparableConcept<_Tp>)
3306*38fd1498Szrj 
3307*38fd1498Szrj       return __b < __a ? pair<const _Tp&, const _Tp&>(__b, __a)
3308*38fd1498Szrj 		       : pair<const _Tp&, const _Tp&>(__a, __b);
3309*38fd1498Szrj     }
3310*38fd1498Szrj 
3311*38fd1498Szrj   /**
3312*38fd1498Szrj    *  @brief  Determines min and max at once as an ordered pair.
3313*38fd1498Szrj    *  @ingroup sorting_algorithms
3314*38fd1498Szrj    *  @param  __a  A thing of arbitrary type.
3315*38fd1498Szrj    *  @param  __b  Another thing of arbitrary type.
3316*38fd1498Szrj    *  @param  __comp  A @link comparison_functors comparison functor @endlink.
3317*38fd1498Szrj    *  @return A pair(__b, __a) if __b is smaller than __a, pair(__a,
3318*38fd1498Szrj    *  __b) otherwise.
3319*38fd1498Szrj   */
3320*38fd1498Szrj   template<typename _Tp, typename _Compare>
3321*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
3322*38fd1498Szrj     inline pair<const _Tp&, const _Tp&>
3323*38fd1498Szrj     minmax(const _Tp& __a, const _Tp& __b, _Compare __comp)
3324*38fd1498Szrj     {
3325*38fd1498Szrj       return __comp(__b, __a) ? pair<const _Tp&, const _Tp&>(__b, __a)
3326*38fd1498Szrj 			      : pair<const _Tp&, const _Tp&>(__a, __b);
3327*38fd1498Szrj     }
3328*38fd1498Szrj 
3329*38fd1498Szrj   template<typename _ForwardIterator, typename _Compare>
3330*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
3331*38fd1498Szrj     pair<_ForwardIterator, _ForwardIterator>
3332*38fd1498Szrj     __minmax_element(_ForwardIterator __first, _ForwardIterator __last,
3333*38fd1498Szrj 		     _Compare __comp)
3334*38fd1498Szrj     {
3335*38fd1498Szrj       _ForwardIterator __next = __first;
3336*38fd1498Szrj       if (__first == __last
3337*38fd1498Szrj 	  || ++__next == __last)
3338*38fd1498Szrj 	return std::make_pair(__first, __first);
3339*38fd1498Szrj 
3340*38fd1498Szrj       _ForwardIterator __min{}, __max{};
3341*38fd1498Szrj       if (__comp(__next, __first))
3342*38fd1498Szrj 	{
3343*38fd1498Szrj 	  __min = __next;
3344*38fd1498Szrj 	  __max = __first;
3345*38fd1498Szrj 	}
3346*38fd1498Szrj       else
3347*38fd1498Szrj 	{
3348*38fd1498Szrj 	  __min = __first;
3349*38fd1498Szrj 	  __max = __next;
3350*38fd1498Szrj 	}
3351*38fd1498Szrj 
3352*38fd1498Szrj       __first = __next;
3353*38fd1498Szrj       ++__first;
3354*38fd1498Szrj 
3355*38fd1498Szrj       while (__first != __last)
3356*38fd1498Szrj 	{
3357*38fd1498Szrj 	  __next = __first;
3358*38fd1498Szrj 	  if (++__next == __last)
3359*38fd1498Szrj 	    {
3360*38fd1498Szrj 	      if (__comp(__first, __min))
3361*38fd1498Szrj 		__min = __first;
3362*38fd1498Szrj 	      else if (!__comp(__first, __max))
3363*38fd1498Szrj 		__max = __first;
3364*38fd1498Szrj 	      break;
3365*38fd1498Szrj 	    }
3366*38fd1498Szrj 
3367*38fd1498Szrj 	  if (__comp(__next, __first))
3368*38fd1498Szrj 	    {
3369*38fd1498Szrj 	      if (__comp(__next, __min))
3370*38fd1498Szrj 		__min = __next;
3371*38fd1498Szrj 	      if (!__comp(__first, __max))
3372*38fd1498Szrj 		__max = __first;
3373*38fd1498Szrj 	    }
3374*38fd1498Szrj 	  else
3375*38fd1498Szrj 	    {
3376*38fd1498Szrj 	      if (__comp(__first, __min))
3377*38fd1498Szrj 		__min = __first;
3378*38fd1498Szrj 	      if (!__comp(__next, __max))
3379*38fd1498Szrj 		__max = __next;
3380*38fd1498Szrj 	    }
3381*38fd1498Szrj 
3382*38fd1498Szrj 	  __first = __next;
3383*38fd1498Szrj 	  ++__first;
3384*38fd1498Szrj 	}
3385*38fd1498Szrj 
3386*38fd1498Szrj       return std::make_pair(__min, __max);
3387*38fd1498Szrj     }
3388*38fd1498Szrj 
3389*38fd1498Szrj   /**
3390*38fd1498Szrj    *  @brief  Return a pair of iterators pointing to the minimum and maximum
3391*38fd1498Szrj    *          elements in a range.
3392*38fd1498Szrj    *  @ingroup sorting_algorithms
3393*38fd1498Szrj    *  @param  __first  Start of range.
3394*38fd1498Szrj    *  @param  __last   End of range.
3395*38fd1498Szrj    *  @return  make_pair(m, M), where m is the first iterator i in
3396*38fd1498Szrj    *           [__first, __last) such that no other element in the range is
3397*38fd1498Szrj    *           smaller, and where M is the last iterator i in [__first, __last)
3398*38fd1498Szrj    *           such that no other element in the range is larger.
3399*38fd1498Szrj   */
3400*38fd1498Szrj   template<typename _ForwardIterator>
3401*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
3402*38fd1498Szrj     inline pair<_ForwardIterator, _ForwardIterator>
3403*38fd1498Szrj     minmax_element(_ForwardIterator __first, _ForwardIterator __last)
3404*38fd1498Szrj     {
3405*38fd1498Szrj       // concept requirements
3406*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
3407*38fd1498Szrj       __glibcxx_function_requires(_LessThanComparableConcept<
3408*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
3409*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
3410*38fd1498Szrj       __glibcxx_requires_irreflexive(__first, __last);
3411*38fd1498Szrj 
3412*38fd1498Szrj       return std::__minmax_element(__first, __last,
3413*38fd1498Szrj 				   __gnu_cxx::__ops::__iter_less_iter());
3414*38fd1498Szrj     }
3415*38fd1498Szrj 
3416*38fd1498Szrj   /**
3417*38fd1498Szrj    *  @brief  Return a pair of iterators pointing to the minimum and maximum
3418*38fd1498Szrj    *          elements in a range.
3419*38fd1498Szrj    *  @ingroup sorting_algorithms
3420*38fd1498Szrj    *  @param  __first  Start of range.
3421*38fd1498Szrj    *  @param  __last   End of range.
3422*38fd1498Szrj    *  @param  __comp   Comparison functor.
3423*38fd1498Szrj    *  @return  make_pair(m, M), where m is the first iterator i in
3424*38fd1498Szrj    *           [__first, __last) such that no other element in the range is
3425*38fd1498Szrj    *           smaller, and where M is the last iterator i in [__first, __last)
3426*38fd1498Szrj    *           such that no other element in the range is larger.
3427*38fd1498Szrj   */
3428*38fd1498Szrj   template<typename _ForwardIterator, typename _Compare>
3429*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
3430*38fd1498Szrj     inline pair<_ForwardIterator, _ForwardIterator>
3431*38fd1498Szrj     minmax_element(_ForwardIterator __first, _ForwardIterator __last,
3432*38fd1498Szrj 		   _Compare __comp)
3433*38fd1498Szrj     {
3434*38fd1498Szrj       // concept requirements
3435*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
3436*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
3437*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type,
3438*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
3439*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
3440*38fd1498Szrj       __glibcxx_requires_irreflexive_pred(__first, __last, __comp);
3441*38fd1498Szrj 
3442*38fd1498Szrj       return std::__minmax_element(__first, __last,
3443*38fd1498Szrj 				   __gnu_cxx::__ops::__iter_comp_iter(__comp));
3444*38fd1498Szrj     }
3445*38fd1498Szrj 
3446*38fd1498Szrj   // N2722 + DR 915.
3447*38fd1498Szrj   template<typename _Tp>
3448*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
3449*38fd1498Szrj     inline _Tp
3450*38fd1498Szrj     min(initializer_list<_Tp> __l)
3451*38fd1498Szrj     { return *std::min_element(__l.begin(), __l.end()); }
3452*38fd1498Szrj 
3453*38fd1498Szrj   template<typename _Tp, typename _Compare>
3454*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
3455*38fd1498Szrj     inline _Tp
3456*38fd1498Szrj     min(initializer_list<_Tp> __l, _Compare __comp)
3457*38fd1498Szrj     { return *std::min_element(__l.begin(), __l.end(), __comp); }
3458*38fd1498Szrj 
3459*38fd1498Szrj   template<typename _Tp>
3460*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
3461*38fd1498Szrj     inline _Tp
3462*38fd1498Szrj     max(initializer_list<_Tp> __l)
3463*38fd1498Szrj     { return *std::max_element(__l.begin(), __l.end()); }
3464*38fd1498Szrj 
3465*38fd1498Szrj   template<typename _Tp, typename _Compare>
3466*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
3467*38fd1498Szrj     inline _Tp
3468*38fd1498Szrj     max(initializer_list<_Tp> __l, _Compare __comp)
3469*38fd1498Szrj     { return *std::max_element(__l.begin(), __l.end(), __comp); }
3470*38fd1498Szrj 
3471*38fd1498Szrj   template<typename _Tp>
3472*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
3473*38fd1498Szrj     inline pair<_Tp, _Tp>
3474*38fd1498Szrj     minmax(initializer_list<_Tp> __l)
3475*38fd1498Szrj     {
3476*38fd1498Szrj       pair<const _Tp*, const _Tp*> __p =
3477*38fd1498Szrj 	std::minmax_element(__l.begin(), __l.end());
3478*38fd1498Szrj       return std::make_pair(*__p.first, *__p.second);
3479*38fd1498Szrj     }
3480*38fd1498Szrj 
3481*38fd1498Szrj   template<typename _Tp, typename _Compare>
3482*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
3483*38fd1498Szrj     inline pair<_Tp, _Tp>
3484*38fd1498Szrj     minmax(initializer_list<_Tp> __l, _Compare __comp)
3485*38fd1498Szrj     {
3486*38fd1498Szrj       pair<const _Tp*, const _Tp*> __p =
3487*38fd1498Szrj 	std::minmax_element(__l.begin(), __l.end(), __comp);
3488*38fd1498Szrj       return std::make_pair(*__p.first, *__p.second);
3489*38fd1498Szrj     }
3490*38fd1498Szrj 
3491*38fd1498Szrj   template<typename _ForwardIterator1, typename _ForwardIterator2,
3492*38fd1498Szrj 	   typename _BinaryPredicate>
3493*38fd1498Szrj     bool
3494*38fd1498Szrj     __is_permutation(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
3495*38fd1498Szrj 		     _ForwardIterator2 __first2, _BinaryPredicate __pred)
3496*38fd1498Szrj     {
3497*38fd1498Szrj       // Efficiently compare identical prefixes:  O(N) if sequences
3498*38fd1498Szrj       // have the same elements in the same order.
3499*38fd1498Szrj       for (; __first1 != __last1; ++__first1, (void)++__first2)
3500*38fd1498Szrj 	if (!__pred(__first1, __first2))
3501*38fd1498Szrj 	  break;
3502*38fd1498Szrj 
3503*38fd1498Szrj       if (__first1 == __last1)
3504*38fd1498Szrj 	return true;
3505*38fd1498Szrj 
3506*38fd1498Szrj       // Establish __last2 assuming equal ranges by iterating over the
3507*38fd1498Szrj       // rest of the list.
3508*38fd1498Szrj       _ForwardIterator2 __last2 = __first2;
3509*38fd1498Szrj       std::advance(__last2, std::distance(__first1, __last1));
3510*38fd1498Szrj       for (_ForwardIterator1 __scan = __first1; __scan != __last1; ++__scan)
3511*38fd1498Szrj 	{
3512*38fd1498Szrj 	  if (__scan != std::__find_if(__first1, __scan,
3513*38fd1498Szrj 			  __gnu_cxx::__ops::__iter_comp_iter(__pred, __scan)))
3514*38fd1498Szrj 	    continue; // We've seen this one before.
3515*38fd1498Szrj 
3516*38fd1498Szrj 	  auto __matches
3517*38fd1498Szrj 	    = std::__count_if(__first2, __last2,
3518*38fd1498Szrj 			__gnu_cxx::__ops::__iter_comp_iter(__pred, __scan));
3519*38fd1498Szrj 	  if (0 == __matches ||
3520*38fd1498Szrj 	      std::__count_if(__scan, __last1,
3521*38fd1498Szrj 			__gnu_cxx::__ops::__iter_comp_iter(__pred, __scan))
3522*38fd1498Szrj 	      != __matches)
3523*38fd1498Szrj 	    return false;
3524*38fd1498Szrj 	}
3525*38fd1498Szrj       return true;
3526*38fd1498Szrj     }
3527*38fd1498Szrj 
3528*38fd1498Szrj   /**
3529*38fd1498Szrj    *  @brief  Checks whether a permutation of the second sequence is equal
3530*38fd1498Szrj    *          to the first sequence.
3531*38fd1498Szrj    *  @ingroup non_mutating_algorithms
3532*38fd1498Szrj    *  @param  __first1  Start of first range.
3533*38fd1498Szrj    *  @param  __last1   End of first range.
3534*38fd1498Szrj    *  @param  __first2  Start of second range.
3535*38fd1498Szrj    *  @return true if there exists a permutation of the elements in the range
3536*38fd1498Szrj    *          [__first2, __first2 + (__last1 - __first1)), beginning with
3537*38fd1498Szrj    *          ForwardIterator2 begin, such that equal(__first1, __last1, begin)
3538*38fd1498Szrj    *          returns true; otherwise, returns false.
3539*38fd1498Szrj   */
3540*38fd1498Szrj   template<typename _ForwardIterator1, typename _ForwardIterator2>
3541*38fd1498Szrj     inline bool
3542*38fd1498Szrj     is_permutation(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
3543*38fd1498Szrj 		   _ForwardIterator2 __first2)
3544*38fd1498Szrj     {
3545*38fd1498Szrj       // concept requirements
3546*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator1>)
3547*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator2>)
3548*38fd1498Szrj       __glibcxx_function_requires(_EqualOpConcept<
3549*38fd1498Szrj 		typename iterator_traits<_ForwardIterator1>::value_type,
3550*38fd1498Szrj 		typename iterator_traits<_ForwardIterator2>::value_type>)
3551*38fd1498Szrj       __glibcxx_requires_valid_range(__first1, __last1);
3552*38fd1498Szrj 
3553*38fd1498Szrj       return std::__is_permutation(__first1, __last1, __first2,
3554*38fd1498Szrj 				   __gnu_cxx::__ops::__iter_equal_to_iter());
3555*38fd1498Szrj     }
3556*38fd1498Szrj 
3557*38fd1498Szrj   /**
3558*38fd1498Szrj    *  @brief  Checks whether a permutation of the second sequence is equal
3559*38fd1498Szrj    *          to the first sequence.
3560*38fd1498Szrj    *  @ingroup non_mutating_algorithms
3561*38fd1498Szrj    *  @param  __first1  Start of first range.
3562*38fd1498Szrj    *  @param  __last1   End of first range.
3563*38fd1498Szrj    *  @param  __first2  Start of second range.
3564*38fd1498Szrj    *  @param  __pred    A binary predicate.
3565*38fd1498Szrj    *  @return true if there exists a permutation of the elements in
3566*38fd1498Szrj    *          the range [__first2, __first2 + (__last1 - __first1)),
3567*38fd1498Szrj    *          beginning with ForwardIterator2 begin, such that
3568*38fd1498Szrj    *          equal(__first1, __last1, __begin, __pred) returns true;
3569*38fd1498Szrj    *          otherwise, returns false.
3570*38fd1498Szrj   */
3571*38fd1498Szrj   template<typename _ForwardIterator1, typename _ForwardIterator2,
3572*38fd1498Szrj 	   typename _BinaryPredicate>
3573*38fd1498Szrj     inline bool
3574*38fd1498Szrj     is_permutation(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
3575*38fd1498Szrj 		   _ForwardIterator2 __first2, _BinaryPredicate __pred)
3576*38fd1498Szrj     {
3577*38fd1498Szrj       // concept requirements
3578*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator1>)
3579*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator2>)
3580*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_BinaryPredicate,
3581*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator1>::value_type,
3582*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator2>::value_type>)
3583*38fd1498Szrj       __glibcxx_requires_valid_range(__first1, __last1);
3584*38fd1498Szrj 
3585*38fd1498Szrj       return std::__is_permutation(__first1, __last1, __first2,
3586*38fd1498Szrj 				   __gnu_cxx::__ops::__iter_comp_iter(__pred));
3587*38fd1498Szrj     }
3588*38fd1498Szrj 
3589*38fd1498Szrj #if __cplusplus > 201103L
3590*38fd1498Szrj   template<typename _ForwardIterator1, typename _ForwardIterator2,
3591*38fd1498Szrj 	   typename _BinaryPredicate>
3592*38fd1498Szrj     bool
3593*38fd1498Szrj     __is_permutation(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
3594*38fd1498Szrj 		     _ForwardIterator2 __first2, _ForwardIterator2 __last2,
3595*38fd1498Szrj 		     _BinaryPredicate __pred)
3596*38fd1498Szrj     {
3597*38fd1498Szrj       using _Cat1
3598*38fd1498Szrj 	= typename iterator_traits<_ForwardIterator1>::iterator_category;
3599*38fd1498Szrj       using _Cat2
3600*38fd1498Szrj 	= typename iterator_traits<_ForwardIterator2>::iterator_category;
3601*38fd1498Szrj       using _It1_is_RA = is_same<_Cat1, random_access_iterator_tag>;
3602*38fd1498Szrj       using _It2_is_RA = is_same<_Cat2, random_access_iterator_tag>;
3603*38fd1498Szrj       constexpr bool __ra_iters = _It1_is_RA() && _It2_is_RA();
3604*38fd1498Szrj       if (__ra_iters)
3605*38fd1498Szrj 	{
3606*38fd1498Szrj 	  auto __d1 = std::distance(__first1, __last1);
3607*38fd1498Szrj 	  auto __d2 = std::distance(__first2, __last2);
3608*38fd1498Szrj 	  if (__d1 != __d2)
3609*38fd1498Szrj 	    return false;
3610*38fd1498Szrj 	}
3611*38fd1498Szrj 
3612*38fd1498Szrj       // Efficiently compare identical prefixes:  O(N) if sequences
3613*38fd1498Szrj       // have the same elements in the same order.
3614*38fd1498Szrj       for (; __first1 != __last1 && __first2 != __last2;
3615*38fd1498Szrj 	  ++__first1, (void)++__first2)
3616*38fd1498Szrj 	if (!__pred(__first1, __first2))
3617*38fd1498Szrj 	  break;
3618*38fd1498Szrj 
3619*38fd1498Szrj       if (__ra_iters)
3620*38fd1498Szrj 	{
3621*38fd1498Szrj 	  if (__first1 == __last1)
3622*38fd1498Szrj 	    return true;
3623*38fd1498Szrj 	}
3624*38fd1498Szrj       else
3625*38fd1498Szrj 	{
3626*38fd1498Szrj 	  auto __d1 = std::distance(__first1, __last1);
3627*38fd1498Szrj 	  auto __d2 = std::distance(__first2, __last2);
3628*38fd1498Szrj 	  if (__d1 == 0 && __d2 == 0)
3629*38fd1498Szrj 	    return true;
3630*38fd1498Szrj 	  if (__d1 != __d2)
3631*38fd1498Szrj 	    return false;
3632*38fd1498Szrj 	}
3633*38fd1498Szrj 
3634*38fd1498Szrj       for (_ForwardIterator1 __scan = __first1; __scan != __last1; ++__scan)
3635*38fd1498Szrj 	{
3636*38fd1498Szrj 	  if (__scan != std::__find_if(__first1, __scan,
3637*38fd1498Szrj 			__gnu_cxx::__ops::__iter_comp_iter(__pred, __scan)))
3638*38fd1498Szrj 	    continue; // We've seen this one before.
3639*38fd1498Szrj 
3640*38fd1498Szrj 	  auto __matches = std::__count_if(__first2, __last2,
3641*38fd1498Szrj 		__gnu_cxx::__ops::__iter_comp_iter(__pred, __scan));
3642*38fd1498Szrj 	  if (0 == __matches
3643*38fd1498Szrj 	      || std::__count_if(__scan, __last1,
3644*38fd1498Szrj 			__gnu_cxx::__ops::__iter_comp_iter(__pred, __scan))
3645*38fd1498Szrj 	      != __matches)
3646*38fd1498Szrj 	    return false;
3647*38fd1498Szrj 	}
3648*38fd1498Szrj       return true;
3649*38fd1498Szrj     }
3650*38fd1498Szrj 
3651*38fd1498Szrj   /**
3652*38fd1498Szrj    *  @brief  Checks whether a permutaion of the second sequence is equal
3653*38fd1498Szrj    *          to the first sequence.
3654*38fd1498Szrj    *  @ingroup non_mutating_algorithms
3655*38fd1498Szrj    *  @param  __first1  Start of first range.
3656*38fd1498Szrj    *  @param  __last1   End of first range.
3657*38fd1498Szrj    *  @param  __first2  Start of second range.
3658*38fd1498Szrj    *  @param  __last2   End of first range.
3659*38fd1498Szrj    *  @return true if there exists a permutation of the elements in the range
3660*38fd1498Szrj    *          [__first2, __last2), beginning with ForwardIterator2 begin,
3661*38fd1498Szrj    *          such that equal(__first1, __last1, begin) returns true;
3662*38fd1498Szrj    *          otherwise, returns false.
3663*38fd1498Szrj   */
3664*38fd1498Szrj   template<typename _ForwardIterator1, typename _ForwardIterator2>
3665*38fd1498Szrj     inline bool
3666*38fd1498Szrj     is_permutation(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
3667*38fd1498Szrj 		   _ForwardIterator2 __first2, _ForwardIterator2 __last2)
3668*38fd1498Szrj     {
3669*38fd1498Szrj       __glibcxx_requires_valid_range(__first1, __last1);
3670*38fd1498Szrj       __glibcxx_requires_valid_range(__first2, __last2);
3671*38fd1498Szrj 
3672*38fd1498Szrj       return
3673*38fd1498Szrj 	std::__is_permutation(__first1, __last1, __first2, __last2,
3674*38fd1498Szrj 			      __gnu_cxx::__ops::__iter_equal_to_iter());
3675*38fd1498Szrj     }
3676*38fd1498Szrj 
3677*38fd1498Szrj   /**
3678*38fd1498Szrj    *  @brief  Checks whether a permutation of the second sequence is equal
3679*38fd1498Szrj    *          to the first sequence.
3680*38fd1498Szrj    *  @ingroup non_mutating_algorithms
3681*38fd1498Szrj    *  @param  __first1  Start of first range.
3682*38fd1498Szrj    *  @param  __last1   End of first range.
3683*38fd1498Szrj    *  @param  __first2  Start of second range.
3684*38fd1498Szrj    *  @param  __last2   End of first range.
3685*38fd1498Szrj    *  @param  __pred    A binary predicate.
3686*38fd1498Szrj    *  @return true if there exists a permutation of the elements in the range
3687*38fd1498Szrj    *          [__first2, __last2), beginning with ForwardIterator2 begin,
3688*38fd1498Szrj    *          such that equal(__first1, __last1, __begin, __pred) returns true;
3689*38fd1498Szrj    *          otherwise, returns false.
3690*38fd1498Szrj   */
3691*38fd1498Szrj   template<typename _ForwardIterator1, typename _ForwardIterator2,
3692*38fd1498Szrj 	   typename _BinaryPredicate>
3693*38fd1498Szrj     inline bool
3694*38fd1498Szrj     is_permutation(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
3695*38fd1498Szrj 		   _ForwardIterator2 __first2, _ForwardIterator2 __last2,
3696*38fd1498Szrj 		   _BinaryPredicate __pred)
3697*38fd1498Szrj     {
3698*38fd1498Szrj       __glibcxx_requires_valid_range(__first1, __last1);
3699*38fd1498Szrj       __glibcxx_requires_valid_range(__first2, __last2);
3700*38fd1498Szrj 
3701*38fd1498Szrj       return std::__is_permutation(__first1, __last1, __first2, __last2,
3702*38fd1498Szrj 				   __gnu_cxx::__ops::__iter_comp_iter(__pred));
3703*38fd1498Szrj     }
3704*38fd1498Szrj 
3705*38fd1498Szrj #if __cplusplus > 201402L
3706*38fd1498Szrj 
3707*38fd1498Szrj #define __cpp_lib_clamp 201603
3708*38fd1498Szrj 
3709*38fd1498Szrj   /**
3710*38fd1498Szrj    *  @brief  Returns the value clamped between lo and hi.
3711*38fd1498Szrj    *  @ingroup sorting_algorithms
3712*38fd1498Szrj    *  @param  __val  A value of arbitrary type.
3713*38fd1498Szrj    *  @param  __lo   A lower limit of arbitrary type.
3714*38fd1498Szrj    *  @param  __hi   An upper limit of arbitrary type.
3715*38fd1498Szrj    *  @return max(__val, __lo) if __val < __hi or min(__val, __hi) otherwise.
3716*38fd1498Szrj    */
3717*38fd1498Szrj   template<typename _Tp>
3718*38fd1498Szrj     constexpr const _Tp&
3719*38fd1498Szrj     clamp(const _Tp& __val, const _Tp& __lo, const _Tp& __hi)
3720*38fd1498Szrj     {
3721*38fd1498Szrj       __glibcxx_assert(!(__hi < __lo));
3722*38fd1498Szrj       return (__val < __lo) ? __lo : (__hi < __val) ? __hi : __val;
3723*38fd1498Szrj     }
3724*38fd1498Szrj 
3725*38fd1498Szrj   /**
3726*38fd1498Szrj    *  @brief  Returns the value clamped between lo and hi.
3727*38fd1498Szrj    *  @ingroup sorting_algorithms
3728*38fd1498Szrj    *  @param  __val   A value of arbitrary type.
3729*38fd1498Szrj    *  @param  __lo    A lower limit of arbitrary type.
3730*38fd1498Szrj    *  @param  __hi    An upper limit of arbitrary type.
3731*38fd1498Szrj    *  @param  __comp  A comparison functor.
3732*38fd1498Szrj    *  @return max(__val, __lo, __comp) if __comp(__val, __hi)
3733*38fd1498Szrj    *	      or min(__val, __hi, __comp) otherwise.
3734*38fd1498Szrj    */
3735*38fd1498Szrj   template<typename _Tp, typename _Compare>
3736*38fd1498Szrj     constexpr const _Tp&
3737*38fd1498Szrj     clamp(const _Tp& __val, const _Tp& __lo, const _Tp& __hi, _Compare __comp)
3738*38fd1498Szrj     {
3739*38fd1498Szrj       __glibcxx_assert(!__comp(__hi, __lo));
3740*38fd1498Szrj       return __comp(__val, __lo) ? __lo : __comp(__hi, __val) ? __hi : __val;
3741*38fd1498Szrj     }
3742*38fd1498Szrj #endif // C++17
3743*38fd1498Szrj #endif // C++14
3744*38fd1498Szrj 
3745*38fd1498Szrj #ifdef _GLIBCXX_USE_C99_STDINT_TR1
3746*38fd1498Szrj   /**
3747*38fd1498Szrj    *  @brief Generate two uniformly distributed integers using a
3748*38fd1498Szrj    *         single distribution invocation.
3749*38fd1498Szrj    *  @param  __b0    The upper bound for the first integer.
3750*38fd1498Szrj    *  @param  __b1    The upper bound for the second integer.
3751*38fd1498Szrj    *  @param  __g     A UniformRandomBitGenerator.
3752*38fd1498Szrj    *  @return  A pair (i, j) with i and j uniformly distributed
3753*38fd1498Szrj    *           over [0, __b0) and [0, __b1), respectively.
3754*38fd1498Szrj    *
3755*38fd1498Szrj    *  Requires: __b0 * __b1 <= __g.max() - __g.min().
3756*38fd1498Szrj    *
3757*38fd1498Szrj    *  Using uniform_int_distribution with a range that is very
3758*38fd1498Szrj    *  small relative to the range of the generator ends up wasting
3759*38fd1498Szrj    *  potentially expensively generated randomness, since
3760*38fd1498Szrj    *  uniform_int_distribution does not store leftover randomness
3761*38fd1498Szrj    *  between invocations.
3762*38fd1498Szrj    *
3763*38fd1498Szrj    *  If we know we want two integers in ranges that are sufficiently
3764*38fd1498Szrj    *  small, we can compose the ranges, use a single distribution
3765*38fd1498Szrj    *  invocation, and significantly reduce the waste.
3766*38fd1498Szrj   */
3767*38fd1498Szrj   template<typename _IntType, typename _UniformRandomBitGenerator>
3768*38fd1498Szrj     pair<_IntType, _IntType>
3769*38fd1498Szrj     __gen_two_uniform_ints(_IntType __b0, _IntType __b1,
3770*38fd1498Szrj 			   _UniformRandomBitGenerator&& __g)
3771*38fd1498Szrj     {
3772*38fd1498Szrj       _IntType __x
3773*38fd1498Szrj 	= uniform_int_distribution<_IntType>{0, (__b0 * __b1) - 1}(__g);
3774*38fd1498Szrj       return std::make_pair(__x / __b1, __x % __b1);
3775*38fd1498Szrj     }
3776*38fd1498Szrj 
3777*38fd1498Szrj   /**
3778*38fd1498Szrj    *  @brief Shuffle the elements of a sequence using a uniform random
3779*38fd1498Szrj    *         number generator.
3780*38fd1498Szrj    *  @ingroup mutating_algorithms
3781*38fd1498Szrj    *  @param  __first   A forward iterator.
3782*38fd1498Szrj    *  @param  __last    A forward iterator.
3783*38fd1498Szrj    *  @param  __g       A UniformRandomNumberGenerator (26.5.1.3).
3784*38fd1498Szrj    *  @return  Nothing.
3785*38fd1498Szrj    *
3786*38fd1498Szrj    *  Reorders the elements in the range @p [__first,__last) using @p __g to
3787*38fd1498Szrj    *  provide random numbers.
3788*38fd1498Szrj   */
3789*38fd1498Szrj   template<typename _RandomAccessIterator,
3790*38fd1498Szrj 	   typename _UniformRandomNumberGenerator>
3791*38fd1498Szrj     void
3792*38fd1498Szrj     shuffle(_RandomAccessIterator __first, _RandomAccessIterator __last,
3793*38fd1498Szrj 	    _UniformRandomNumberGenerator&& __g)
3794*38fd1498Szrj     {
3795*38fd1498Szrj       // concept requirements
3796*38fd1498Szrj       __glibcxx_function_requires(_Mutable_RandomAccessIteratorConcept<
3797*38fd1498Szrj 	    _RandomAccessIterator>)
3798*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
3799*38fd1498Szrj 
3800*38fd1498Szrj       if (__first == __last)
3801*38fd1498Szrj 	return;
3802*38fd1498Szrj 
3803*38fd1498Szrj       typedef typename iterator_traits<_RandomAccessIterator>::difference_type
3804*38fd1498Szrj 	_DistanceType;
3805*38fd1498Szrj 
3806*38fd1498Szrj       typedef typename std::make_unsigned<_DistanceType>::type __ud_type;
3807*38fd1498Szrj       typedef typename std::uniform_int_distribution<__ud_type> __distr_type;
3808*38fd1498Szrj       typedef typename __distr_type::param_type __p_type;
3809*38fd1498Szrj 
3810*38fd1498Szrj       typedef typename remove_reference<_UniformRandomNumberGenerator>::type
3811*38fd1498Szrj 	_Gen;
3812*38fd1498Szrj       typedef typename common_type<typename _Gen::result_type, __ud_type>::type
3813*38fd1498Szrj 	__uc_type;
3814*38fd1498Szrj 
3815*38fd1498Szrj       const __uc_type __urngrange = __g.max() - __g.min();
3816*38fd1498Szrj       const __uc_type __urange = __uc_type(__last - __first);
3817*38fd1498Szrj 
3818*38fd1498Szrj       if (__urngrange / __urange >= __urange)
3819*38fd1498Szrj         // I.e. (__urngrange >= __urange * __urange) but without wrap issues.
3820*38fd1498Szrj       {
3821*38fd1498Szrj 	_RandomAccessIterator __i = __first + 1;
3822*38fd1498Szrj 
3823*38fd1498Szrj 	// Since we know the range isn't empty, an even number of elements
3824*38fd1498Szrj 	// means an uneven number of elements /to swap/, in which case we
3825*38fd1498Szrj 	// do the first one up front:
3826*38fd1498Szrj 
3827*38fd1498Szrj 	if ((__urange % 2) == 0)
3828*38fd1498Szrj 	{
3829*38fd1498Szrj 	  __distr_type __d{0, 1};
3830*38fd1498Szrj 	  std::iter_swap(__i++, __first + __d(__g));
3831*38fd1498Szrj 	}
3832*38fd1498Szrj 
3833*38fd1498Szrj 	// Now we know that __last - __i is even, so we do the rest in pairs,
3834*38fd1498Szrj 	// using a single distribution invocation to produce swap positions
3835*38fd1498Szrj 	// for two successive elements at a time:
3836*38fd1498Szrj 
3837*38fd1498Szrj 	while (__i != __last)
3838*38fd1498Szrj 	{
3839*38fd1498Szrj 	  const __uc_type __swap_range = __uc_type(__i - __first) + 1;
3840*38fd1498Szrj 
3841*38fd1498Szrj 	  const pair<__uc_type, __uc_type> __pospos =
3842*38fd1498Szrj 	    __gen_two_uniform_ints(__swap_range, __swap_range + 1, __g);
3843*38fd1498Szrj 
3844*38fd1498Szrj 	  std::iter_swap(__i++, __first + __pospos.first);
3845*38fd1498Szrj 	  std::iter_swap(__i++, __first + __pospos.second);
3846*38fd1498Szrj 	}
3847*38fd1498Szrj 
3848*38fd1498Szrj 	return;
3849*38fd1498Szrj       }
3850*38fd1498Szrj 
3851*38fd1498Szrj       __distr_type __d;
3852*38fd1498Szrj 
3853*38fd1498Szrj       for (_RandomAccessIterator __i = __first + 1; __i != __last; ++__i)
3854*38fd1498Szrj 	std::iter_swap(__i, __first + __d(__g, __p_type(0, __i - __first)));
3855*38fd1498Szrj     }
3856*38fd1498Szrj #endif
3857*38fd1498Szrj 
3858*38fd1498Szrj #endif // C++11
3859*38fd1498Szrj 
3860*38fd1498Szrj _GLIBCXX_BEGIN_NAMESPACE_ALGO
3861*38fd1498Szrj 
3862*38fd1498Szrj   /**
3863*38fd1498Szrj    *  @brief Apply a function to every element of a sequence.
3864*38fd1498Szrj    *  @ingroup non_mutating_algorithms
3865*38fd1498Szrj    *  @param  __first  An input iterator.
3866*38fd1498Szrj    *  @param  __last   An input iterator.
3867*38fd1498Szrj    *  @param  __f      A unary function object.
3868*38fd1498Szrj    *  @return   @p __f
3869*38fd1498Szrj    *
3870*38fd1498Szrj    *  Applies the function object @p __f to each element in the range
3871*38fd1498Szrj    *  @p [first,last).  @p __f must not modify the order of the sequence.
3872*38fd1498Szrj    *  If @p __f has a return value it is ignored.
3873*38fd1498Szrj   */
3874*38fd1498Szrj   template<typename _InputIterator, typename _Function>
3875*38fd1498Szrj     _Function
3876*38fd1498Szrj     for_each(_InputIterator __first, _InputIterator __last, _Function __f)
3877*38fd1498Szrj     {
3878*38fd1498Szrj       // concept requirements
3879*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
3880*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
3881*38fd1498Szrj       for (; __first != __last; ++__first)
3882*38fd1498Szrj 	__f(*__first);
3883*38fd1498Szrj       return __f; // N.B. [alg.foreach] says std::move(f) but it's redundant.
3884*38fd1498Szrj     }
3885*38fd1498Szrj 
3886*38fd1498Szrj   /**
3887*38fd1498Szrj    *  @brief Find the first occurrence of a value in a sequence.
3888*38fd1498Szrj    *  @ingroup non_mutating_algorithms
3889*38fd1498Szrj    *  @param  __first  An input iterator.
3890*38fd1498Szrj    *  @param  __last   An input iterator.
3891*38fd1498Szrj    *  @param  __val    The value to find.
3892*38fd1498Szrj    *  @return   The first iterator @c i in the range @p [__first,__last)
3893*38fd1498Szrj    *  such that @c *i == @p __val, or @p __last if no such iterator exists.
3894*38fd1498Szrj   */
3895*38fd1498Szrj   template<typename _InputIterator, typename _Tp>
3896*38fd1498Szrj     inline _InputIterator
3897*38fd1498Szrj     find(_InputIterator __first, _InputIterator __last,
3898*38fd1498Szrj 	 const _Tp& __val)
3899*38fd1498Szrj     {
3900*38fd1498Szrj       // concept requirements
3901*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
3902*38fd1498Szrj       __glibcxx_function_requires(_EqualOpConcept<
3903*38fd1498Szrj 		typename iterator_traits<_InputIterator>::value_type, _Tp>)
3904*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
3905*38fd1498Szrj       return std::__find_if(__first, __last,
3906*38fd1498Szrj 			    __gnu_cxx::__ops::__iter_equals_val(__val));
3907*38fd1498Szrj     }
3908*38fd1498Szrj 
3909*38fd1498Szrj   /**
3910*38fd1498Szrj    *  @brief Find the first element in a sequence for which a
3911*38fd1498Szrj    *         predicate is true.
3912*38fd1498Szrj    *  @ingroup non_mutating_algorithms
3913*38fd1498Szrj    *  @param  __first  An input iterator.
3914*38fd1498Szrj    *  @param  __last   An input iterator.
3915*38fd1498Szrj    *  @param  __pred   A predicate.
3916*38fd1498Szrj    *  @return   The first iterator @c i in the range @p [__first,__last)
3917*38fd1498Szrj    *  such that @p __pred(*i) is true, or @p __last if no such iterator exists.
3918*38fd1498Szrj   */
3919*38fd1498Szrj   template<typename _InputIterator, typename _Predicate>
3920*38fd1498Szrj     inline _InputIterator
3921*38fd1498Szrj     find_if(_InputIterator __first, _InputIterator __last,
3922*38fd1498Szrj 	    _Predicate __pred)
3923*38fd1498Szrj     {
3924*38fd1498Szrj       // concept requirements
3925*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
3926*38fd1498Szrj       __glibcxx_function_requires(_UnaryPredicateConcept<_Predicate,
3927*38fd1498Szrj 	      typename iterator_traits<_InputIterator>::value_type>)
3928*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
3929*38fd1498Szrj 
3930*38fd1498Szrj       return std::__find_if(__first, __last,
3931*38fd1498Szrj 			    __gnu_cxx::__ops::__pred_iter(__pred));
3932*38fd1498Szrj     }
3933*38fd1498Szrj 
3934*38fd1498Szrj   /**
3935*38fd1498Szrj    *  @brief  Find element from a set in a sequence.
3936*38fd1498Szrj    *  @ingroup non_mutating_algorithms
3937*38fd1498Szrj    *  @param  __first1  Start of range to search.
3938*38fd1498Szrj    *  @param  __last1   End of range to search.
3939*38fd1498Szrj    *  @param  __first2  Start of match candidates.
3940*38fd1498Szrj    *  @param  __last2   End of match candidates.
3941*38fd1498Szrj    *  @return   The first iterator @c i in the range
3942*38fd1498Szrj    *  @p [__first1,__last1) such that @c *i == @p *(i2) such that i2 is an
3943*38fd1498Szrj    *  iterator in [__first2,__last2), or @p __last1 if no such iterator exists.
3944*38fd1498Szrj    *
3945*38fd1498Szrj    *  Searches the range @p [__first1,__last1) for an element that is
3946*38fd1498Szrj    *  equal to some element in the range [__first2,__last2).  If
3947*38fd1498Szrj    *  found, returns an iterator in the range [__first1,__last1),
3948*38fd1498Szrj    *  otherwise returns @p __last1.
3949*38fd1498Szrj   */
3950*38fd1498Szrj   template<typename _InputIterator, typename _ForwardIterator>
3951*38fd1498Szrj     _InputIterator
3952*38fd1498Szrj     find_first_of(_InputIterator __first1, _InputIterator __last1,
3953*38fd1498Szrj 		  _ForwardIterator __first2, _ForwardIterator __last2)
3954*38fd1498Szrj     {
3955*38fd1498Szrj       // concept requirements
3956*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
3957*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
3958*38fd1498Szrj       __glibcxx_function_requires(_EqualOpConcept<
3959*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type,
3960*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
3961*38fd1498Szrj       __glibcxx_requires_valid_range(__first1, __last1);
3962*38fd1498Szrj       __glibcxx_requires_valid_range(__first2, __last2);
3963*38fd1498Szrj 
3964*38fd1498Szrj       for (; __first1 != __last1; ++__first1)
3965*38fd1498Szrj 	for (_ForwardIterator __iter = __first2; __iter != __last2; ++__iter)
3966*38fd1498Szrj 	  if (*__first1 == *__iter)
3967*38fd1498Szrj 	    return __first1;
3968*38fd1498Szrj       return __last1;
3969*38fd1498Szrj     }
3970*38fd1498Szrj 
3971*38fd1498Szrj   /**
3972*38fd1498Szrj    *  @brief  Find element from a set in a sequence using a predicate.
3973*38fd1498Szrj    *  @ingroup non_mutating_algorithms
3974*38fd1498Szrj    *  @param  __first1  Start of range to search.
3975*38fd1498Szrj    *  @param  __last1   End of range to search.
3976*38fd1498Szrj    *  @param  __first2  Start of match candidates.
3977*38fd1498Szrj    *  @param  __last2   End of match candidates.
3978*38fd1498Szrj    *  @param  __comp    Predicate to use.
3979*38fd1498Szrj    *  @return   The first iterator @c i in the range
3980*38fd1498Szrj    *  @p [__first1,__last1) such that @c comp(*i, @p *(i2)) is true
3981*38fd1498Szrj    *  and i2 is an iterator in [__first2,__last2), or @p __last1 if no
3982*38fd1498Szrj    *  such iterator exists.
3983*38fd1498Szrj    *
3984*38fd1498Szrj 
3985*38fd1498Szrj    *  Searches the range @p [__first1,__last1) for an element that is
3986*38fd1498Szrj    *  equal to some element in the range [__first2,__last2).  If
3987*38fd1498Szrj    *  found, returns an iterator in the range [__first1,__last1),
3988*38fd1498Szrj    *  otherwise returns @p __last1.
3989*38fd1498Szrj   */
3990*38fd1498Szrj   template<typename _InputIterator, typename _ForwardIterator,
3991*38fd1498Szrj 	   typename _BinaryPredicate>
3992*38fd1498Szrj     _InputIterator
3993*38fd1498Szrj     find_first_of(_InputIterator __first1, _InputIterator __last1,
3994*38fd1498Szrj 		  _ForwardIterator __first2, _ForwardIterator __last2,
3995*38fd1498Szrj 		  _BinaryPredicate __comp)
3996*38fd1498Szrj     {
3997*38fd1498Szrj       // concept requirements
3998*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
3999*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
4000*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_BinaryPredicate,
4001*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type,
4002*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
4003*38fd1498Szrj       __glibcxx_requires_valid_range(__first1, __last1);
4004*38fd1498Szrj       __glibcxx_requires_valid_range(__first2, __last2);
4005*38fd1498Szrj 
4006*38fd1498Szrj       for (; __first1 != __last1; ++__first1)
4007*38fd1498Szrj 	for (_ForwardIterator __iter = __first2; __iter != __last2; ++__iter)
4008*38fd1498Szrj 	  if (__comp(*__first1, *__iter))
4009*38fd1498Szrj 	    return __first1;
4010*38fd1498Szrj       return __last1;
4011*38fd1498Szrj     }
4012*38fd1498Szrj 
4013*38fd1498Szrj   /**
4014*38fd1498Szrj    *  @brief Find two adjacent values in a sequence that are equal.
4015*38fd1498Szrj    *  @ingroup non_mutating_algorithms
4016*38fd1498Szrj    *  @param  __first  A forward iterator.
4017*38fd1498Szrj    *  @param  __last   A forward iterator.
4018*38fd1498Szrj    *  @return   The first iterator @c i such that @c i and @c i+1 are both
4019*38fd1498Szrj    *  valid iterators in @p [__first,__last) and such that @c *i == @c *(i+1),
4020*38fd1498Szrj    *  or @p __last if no such iterator exists.
4021*38fd1498Szrj   */
4022*38fd1498Szrj   template<typename _ForwardIterator>
4023*38fd1498Szrj     inline _ForwardIterator
4024*38fd1498Szrj     adjacent_find(_ForwardIterator __first, _ForwardIterator __last)
4025*38fd1498Szrj     {
4026*38fd1498Szrj       // concept requirements
4027*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
4028*38fd1498Szrj       __glibcxx_function_requires(_EqualityComparableConcept<
4029*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
4030*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4031*38fd1498Szrj 
4032*38fd1498Szrj       return std::__adjacent_find(__first, __last,
4033*38fd1498Szrj 				  __gnu_cxx::__ops::__iter_equal_to_iter());
4034*38fd1498Szrj     }
4035*38fd1498Szrj 
4036*38fd1498Szrj   /**
4037*38fd1498Szrj    *  @brief Find two adjacent values in a sequence using a predicate.
4038*38fd1498Szrj    *  @ingroup non_mutating_algorithms
4039*38fd1498Szrj    *  @param  __first         A forward iterator.
4040*38fd1498Szrj    *  @param  __last          A forward iterator.
4041*38fd1498Szrj    *  @param  __binary_pred   A binary predicate.
4042*38fd1498Szrj    *  @return   The first iterator @c i such that @c i and @c i+1 are both
4043*38fd1498Szrj    *  valid iterators in @p [__first,__last) and such that
4044*38fd1498Szrj    *  @p __binary_pred(*i,*(i+1)) is true, or @p __last if no such iterator
4045*38fd1498Szrj    *  exists.
4046*38fd1498Szrj   */
4047*38fd1498Szrj   template<typename _ForwardIterator, typename _BinaryPredicate>
4048*38fd1498Szrj     inline _ForwardIterator
4049*38fd1498Szrj     adjacent_find(_ForwardIterator __first, _ForwardIterator __last,
4050*38fd1498Szrj 		  _BinaryPredicate __binary_pred)
4051*38fd1498Szrj     {
4052*38fd1498Szrj       // concept requirements
4053*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
4054*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_BinaryPredicate,
4055*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type,
4056*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
4057*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4058*38fd1498Szrj 
4059*38fd1498Szrj       return std::__adjacent_find(__first, __last,
4060*38fd1498Szrj 			__gnu_cxx::__ops::__iter_comp_iter(__binary_pred));
4061*38fd1498Szrj     }
4062*38fd1498Szrj 
4063*38fd1498Szrj   /**
4064*38fd1498Szrj    *  @brief Count the number of copies of a value in a sequence.
4065*38fd1498Szrj    *  @ingroup non_mutating_algorithms
4066*38fd1498Szrj    *  @param  __first  An input iterator.
4067*38fd1498Szrj    *  @param  __last   An input iterator.
4068*38fd1498Szrj    *  @param  __value  The value to be counted.
4069*38fd1498Szrj    *  @return   The number of iterators @c i in the range @p [__first,__last)
4070*38fd1498Szrj    *  for which @c *i == @p __value
4071*38fd1498Szrj   */
4072*38fd1498Szrj   template<typename _InputIterator, typename _Tp>
4073*38fd1498Szrj     inline typename iterator_traits<_InputIterator>::difference_type
4074*38fd1498Szrj     count(_InputIterator __first, _InputIterator __last, const _Tp& __value)
4075*38fd1498Szrj     {
4076*38fd1498Szrj       // concept requirements
4077*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
4078*38fd1498Szrj       __glibcxx_function_requires(_EqualOpConcept<
4079*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type, _Tp>)
4080*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4081*38fd1498Szrj 
4082*38fd1498Szrj       return std::__count_if(__first, __last,
4083*38fd1498Szrj 			     __gnu_cxx::__ops::__iter_equals_val(__value));
4084*38fd1498Szrj     }
4085*38fd1498Szrj 
4086*38fd1498Szrj   /**
4087*38fd1498Szrj    *  @brief Count the elements of a sequence for which a predicate is true.
4088*38fd1498Szrj    *  @ingroup non_mutating_algorithms
4089*38fd1498Szrj    *  @param  __first  An input iterator.
4090*38fd1498Szrj    *  @param  __last   An input iterator.
4091*38fd1498Szrj    *  @param  __pred   A predicate.
4092*38fd1498Szrj    *  @return   The number of iterators @c i in the range @p [__first,__last)
4093*38fd1498Szrj    *  for which @p __pred(*i) is true.
4094*38fd1498Szrj   */
4095*38fd1498Szrj   template<typename _InputIterator, typename _Predicate>
4096*38fd1498Szrj     inline typename iterator_traits<_InputIterator>::difference_type
4097*38fd1498Szrj     count_if(_InputIterator __first, _InputIterator __last, _Predicate __pred)
4098*38fd1498Szrj     {
4099*38fd1498Szrj       // concept requirements
4100*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
4101*38fd1498Szrj       __glibcxx_function_requires(_UnaryPredicateConcept<_Predicate,
4102*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
4103*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4104*38fd1498Szrj 
4105*38fd1498Szrj       return std::__count_if(__first, __last,
4106*38fd1498Szrj 			     __gnu_cxx::__ops::__pred_iter(__pred));
4107*38fd1498Szrj     }
4108*38fd1498Szrj 
4109*38fd1498Szrj   /**
4110*38fd1498Szrj    *  @brief Search a sequence for a matching sub-sequence.
4111*38fd1498Szrj    *  @ingroup non_mutating_algorithms
4112*38fd1498Szrj    *  @param  __first1  A forward iterator.
4113*38fd1498Szrj    *  @param  __last1   A forward iterator.
4114*38fd1498Szrj    *  @param  __first2  A forward iterator.
4115*38fd1498Szrj    *  @param  __last2   A forward iterator.
4116*38fd1498Szrj    *  @return The first iterator @c i in the range @p
4117*38fd1498Szrj    *  [__first1,__last1-(__last2-__first2)) such that @c *(i+N) == @p
4118*38fd1498Szrj    *  *(__first2+N) for each @c N in the range @p
4119*38fd1498Szrj    *  [0,__last2-__first2), or @p __last1 if no such iterator exists.
4120*38fd1498Szrj    *
4121*38fd1498Szrj    *  Searches the range @p [__first1,__last1) for a sub-sequence that
4122*38fd1498Szrj    *  compares equal value-by-value with the sequence given by @p
4123*38fd1498Szrj    *  [__first2,__last2) and returns an iterator to the first element
4124*38fd1498Szrj    *  of the sub-sequence, or @p __last1 if the sub-sequence is not
4125*38fd1498Szrj    *  found.
4126*38fd1498Szrj    *
4127*38fd1498Szrj    *  Because the sub-sequence must lie completely within the range @p
4128*38fd1498Szrj    *  [__first1,__last1) it must start at a position less than @p
4129*38fd1498Szrj    *  __last1-(__last2-__first2) where @p __last2-__first2 is the
4130*38fd1498Szrj    *  length of the sub-sequence.
4131*38fd1498Szrj    *
4132*38fd1498Szrj    *  This means that the returned iterator @c i will be in the range
4133*38fd1498Szrj    *  @p [__first1,__last1-(__last2-__first2))
4134*38fd1498Szrj   */
4135*38fd1498Szrj   template<typename _ForwardIterator1, typename _ForwardIterator2>
4136*38fd1498Szrj     inline _ForwardIterator1
4137*38fd1498Szrj     search(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
4138*38fd1498Szrj 	   _ForwardIterator2 __first2, _ForwardIterator2 __last2)
4139*38fd1498Szrj     {
4140*38fd1498Szrj       // concept requirements
4141*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator1>)
4142*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator2>)
4143*38fd1498Szrj       __glibcxx_function_requires(_EqualOpConcept<
4144*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator1>::value_type,
4145*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator2>::value_type>)
4146*38fd1498Szrj       __glibcxx_requires_valid_range(__first1, __last1);
4147*38fd1498Szrj       __glibcxx_requires_valid_range(__first2, __last2);
4148*38fd1498Szrj 
4149*38fd1498Szrj       return std::__search(__first1, __last1, __first2, __last2,
4150*38fd1498Szrj 			   __gnu_cxx::__ops::__iter_equal_to_iter());
4151*38fd1498Szrj     }
4152*38fd1498Szrj 
4153*38fd1498Szrj   /**
4154*38fd1498Szrj    *  @brief Search a sequence for a matching sub-sequence using a predicate.
4155*38fd1498Szrj    *  @ingroup non_mutating_algorithms
4156*38fd1498Szrj    *  @param  __first1     A forward iterator.
4157*38fd1498Szrj    *  @param  __last1      A forward iterator.
4158*38fd1498Szrj    *  @param  __first2     A forward iterator.
4159*38fd1498Szrj    *  @param  __last2      A forward iterator.
4160*38fd1498Szrj    *  @param  __predicate  A binary predicate.
4161*38fd1498Szrj    *  @return   The first iterator @c i in the range
4162*38fd1498Szrj    *  @p [__first1,__last1-(__last2-__first2)) such that
4163*38fd1498Szrj    *  @p __predicate(*(i+N),*(__first2+N)) is true for each @c N in the range
4164*38fd1498Szrj    *  @p [0,__last2-__first2), or @p __last1 if no such iterator exists.
4165*38fd1498Szrj    *
4166*38fd1498Szrj    *  Searches the range @p [__first1,__last1) for a sub-sequence that
4167*38fd1498Szrj    *  compares equal value-by-value with the sequence given by @p
4168*38fd1498Szrj    *  [__first2,__last2), using @p __predicate to determine equality,
4169*38fd1498Szrj    *  and returns an iterator to the first element of the
4170*38fd1498Szrj    *  sub-sequence, or @p __last1 if no such iterator exists.
4171*38fd1498Szrj    *
4172*38fd1498Szrj    *  @see search(_ForwardIter1, _ForwardIter1, _ForwardIter2, _ForwardIter2)
4173*38fd1498Szrj   */
4174*38fd1498Szrj   template<typename _ForwardIterator1, typename _ForwardIterator2,
4175*38fd1498Szrj 	   typename _BinaryPredicate>
4176*38fd1498Szrj     inline _ForwardIterator1
4177*38fd1498Szrj     search(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
4178*38fd1498Szrj 	   _ForwardIterator2 __first2, _ForwardIterator2 __last2,
4179*38fd1498Szrj 	   _BinaryPredicate  __predicate)
4180*38fd1498Szrj     {
4181*38fd1498Szrj       // concept requirements
4182*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator1>)
4183*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator2>)
4184*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_BinaryPredicate,
4185*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator1>::value_type,
4186*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator2>::value_type>)
4187*38fd1498Szrj       __glibcxx_requires_valid_range(__first1, __last1);
4188*38fd1498Szrj       __glibcxx_requires_valid_range(__first2, __last2);
4189*38fd1498Szrj 
4190*38fd1498Szrj       return std::__search(__first1, __last1, __first2, __last2,
4191*38fd1498Szrj 			   __gnu_cxx::__ops::__iter_comp_iter(__predicate));
4192*38fd1498Szrj     }
4193*38fd1498Szrj 
4194*38fd1498Szrj   /**
4195*38fd1498Szrj    *  @brief Search a sequence for a number of consecutive values.
4196*38fd1498Szrj    *  @ingroup non_mutating_algorithms
4197*38fd1498Szrj    *  @param  __first  A forward iterator.
4198*38fd1498Szrj    *  @param  __last   A forward iterator.
4199*38fd1498Szrj    *  @param  __count  The number of consecutive values.
4200*38fd1498Szrj    *  @param  __val    The value to find.
4201*38fd1498Szrj    *  @return The first iterator @c i in the range @p
4202*38fd1498Szrj    *  [__first,__last-__count) such that @c *(i+N) == @p __val for
4203*38fd1498Szrj    *  each @c N in the range @p [0,__count), or @p __last if no such
4204*38fd1498Szrj    *  iterator exists.
4205*38fd1498Szrj    *
4206*38fd1498Szrj    *  Searches the range @p [__first,__last) for @p count consecutive elements
4207*38fd1498Szrj    *  equal to @p __val.
4208*38fd1498Szrj   */
4209*38fd1498Szrj   template<typename _ForwardIterator, typename _Integer, typename _Tp>
4210*38fd1498Szrj     inline _ForwardIterator
4211*38fd1498Szrj     search_n(_ForwardIterator __first, _ForwardIterator __last,
4212*38fd1498Szrj 	     _Integer __count, const _Tp& __val)
4213*38fd1498Szrj     {
4214*38fd1498Szrj       // concept requirements
4215*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
4216*38fd1498Szrj       __glibcxx_function_requires(_EqualOpConcept<
4217*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type, _Tp>)
4218*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4219*38fd1498Szrj 
4220*38fd1498Szrj       return std::__search_n(__first, __last, __count,
4221*38fd1498Szrj 			     __gnu_cxx::__ops::__iter_equals_val(__val));
4222*38fd1498Szrj     }
4223*38fd1498Szrj 
4224*38fd1498Szrj 
4225*38fd1498Szrj   /**
4226*38fd1498Szrj    *  @brief Search a sequence for a number of consecutive values using a
4227*38fd1498Szrj    *         predicate.
4228*38fd1498Szrj    *  @ingroup non_mutating_algorithms
4229*38fd1498Szrj    *  @param  __first        A forward iterator.
4230*38fd1498Szrj    *  @param  __last         A forward iterator.
4231*38fd1498Szrj    *  @param  __count        The number of consecutive values.
4232*38fd1498Szrj    *  @param  __val          The value to find.
4233*38fd1498Szrj    *  @param  __binary_pred  A binary predicate.
4234*38fd1498Szrj    *  @return The first iterator @c i in the range @p
4235*38fd1498Szrj    *  [__first,__last-__count) such that @p
4236*38fd1498Szrj    *  __binary_pred(*(i+N),__val) is true for each @c N in the range
4237*38fd1498Szrj    *  @p [0,__count), or @p __last if no such iterator exists.
4238*38fd1498Szrj    *
4239*38fd1498Szrj    *  Searches the range @p [__first,__last) for @p __count
4240*38fd1498Szrj    *  consecutive elements for which the predicate returns true.
4241*38fd1498Szrj   */
4242*38fd1498Szrj   template<typename _ForwardIterator, typename _Integer, typename _Tp,
4243*38fd1498Szrj 	   typename _BinaryPredicate>
4244*38fd1498Szrj     inline _ForwardIterator
4245*38fd1498Szrj     search_n(_ForwardIterator __first, _ForwardIterator __last,
4246*38fd1498Szrj 	     _Integer __count, const _Tp& __val,
4247*38fd1498Szrj 	     _BinaryPredicate __binary_pred)
4248*38fd1498Szrj     {
4249*38fd1498Szrj       // concept requirements
4250*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
4251*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_BinaryPredicate,
4252*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type, _Tp>)
4253*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4254*38fd1498Szrj 
4255*38fd1498Szrj       return std::__search_n(__first, __last, __count,
4256*38fd1498Szrj 		__gnu_cxx::__ops::__iter_comp_val(__binary_pred, __val));
4257*38fd1498Szrj     }
4258*38fd1498Szrj 
4259*38fd1498Szrj #if __cplusplus > 201402L
4260*38fd1498Szrj   /** @brief Search a sequence using a Searcher object.
4261*38fd1498Szrj    *
4262*38fd1498Szrj    *  @param  __first        A forward iterator.
4263*38fd1498Szrj    *  @param  __last         A forward iterator.
4264*38fd1498Szrj    *  @param  __searcher     A callable object.
4265*38fd1498Szrj    *  @return @p __searcher(__first,__last).first
4266*38fd1498Szrj   */
4267*38fd1498Szrj   template<typename _ForwardIterator, typename _Searcher>
4268*38fd1498Szrj     inline _ForwardIterator
4269*38fd1498Szrj     search(_ForwardIterator __first, _ForwardIterator __last,
4270*38fd1498Szrj 	   const _Searcher& __searcher)
4271*38fd1498Szrj     { return __searcher(__first, __last).first; }
4272*38fd1498Szrj #endif
4273*38fd1498Szrj 
4274*38fd1498Szrj   /**
4275*38fd1498Szrj    *  @brief Perform an operation on a sequence.
4276*38fd1498Szrj    *  @ingroup mutating_algorithms
4277*38fd1498Szrj    *  @param  __first     An input iterator.
4278*38fd1498Szrj    *  @param  __last      An input iterator.
4279*38fd1498Szrj    *  @param  __result    An output iterator.
4280*38fd1498Szrj    *  @param  __unary_op  A unary operator.
4281*38fd1498Szrj    *  @return   An output iterator equal to @p __result+(__last-__first).
4282*38fd1498Szrj    *
4283*38fd1498Szrj    *  Applies the operator to each element in the input range and assigns
4284*38fd1498Szrj    *  the results to successive elements of the output sequence.
4285*38fd1498Szrj    *  Evaluates @p *(__result+N)=unary_op(*(__first+N)) for each @c N in the
4286*38fd1498Szrj    *  range @p [0,__last-__first).
4287*38fd1498Szrj    *
4288*38fd1498Szrj    *  @p unary_op must not alter its argument.
4289*38fd1498Szrj   */
4290*38fd1498Szrj   template<typename _InputIterator, typename _OutputIterator,
4291*38fd1498Szrj 	   typename _UnaryOperation>
4292*38fd1498Szrj     _OutputIterator
4293*38fd1498Szrj     transform(_InputIterator __first, _InputIterator __last,
4294*38fd1498Szrj 	      _OutputIterator __result, _UnaryOperation __unary_op)
4295*38fd1498Szrj     {
4296*38fd1498Szrj       // concept requirements
4297*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
4298*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
4299*38fd1498Szrj 	    // "the type returned by a _UnaryOperation"
4300*38fd1498Szrj 	    __typeof__(__unary_op(*__first))>)
4301*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4302*38fd1498Szrj 
4303*38fd1498Szrj       for (; __first != __last; ++__first, (void)++__result)
4304*38fd1498Szrj 	*__result = __unary_op(*__first);
4305*38fd1498Szrj       return __result;
4306*38fd1498Szrj     }
4307*38fd1498Szrj 
4308*38fd1498Szrj   /**
4309*38fd1498Szrj    *  @brief Perform an operation on corresponding elements of two sequences.
4310*38fd1498Szrj    *  @ingroup mutating_algorithms
4311*38fd1498Szrj    *  @param  __first1     An input iterator.
4312*38fd1498Szrj    *  @param  __last1      An input iterator.
4313*38fd1498Szrj    *  @param  __first2     An input iterator.
4314*38fd1498Szrj    *  @param  __result     An output iterator.
4315*38fd1498Szrj    *  @param  __binary_op  A binary operator.
4316*38fd1498Szrj    *  @return   An output iterator equal to @p result+(last-first).
4317*38fd1498Szrj    *
4318*38fd1498Szrj    *  Applies the operator to the corresponding elements in the two
4319*38fd1498Szrj    *  input ranges and assigns the results to successive elements of the
4320*38fd1498Szrj    *  output sequence.
4321*38fd1498Szrj    *  Evaluates @p
4322*38fd1498Szrj    *  *(__result+N)=__binary_op(*(__first1+N),*(__first2+N)) for each
4323*38fd1498Szrj    *  @c N in the range @p [0,__last1-__first1).
4324*38fd1498Szrj    *
4325*38fd1498Szrj    *  @p binary_op must not alter either of its arguments.
4326*38fd1498Szrj   */
4327*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
4328*38fd1498Szrj 	   typename _OutputIterator, typename _BinaryOperation>
4329*38fd1498Szrj     _OutputIterator
4330*38fd1498Szrj     transform(_InputIterator1 __first1, _InputIterator1 __last1,
4331*38fd1498Szrj 	      _InputIterator2 __first2, _OutputIterator __result,
4332*38fd1498Szrj 	      _BinaryOperation __binary_op)
4333*38fd1498Szrj     {
4334*38fd1498Szrj       // concept requirements
4335*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator1>)
4336*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator2>)
4337*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
4338*38fd1498Szrj 	    // "the type returned by a _BinaryOperation"
4339*38fd1498Szrj 	    __typeof__(__binary_op(*__first1,*__first2))>)
4340*38fd1498Szrj       __glibcxx_requires_valid_range(__first1, __last1);
4341*38fd1498Szrj 
4342*38fd1498Szrj       for (; __first1 != __last1; ++__first1, (void)++__first2, ++__result)
4343*38fd1498Szrj 	*__result = __binary_op(*__first1, *__first2);
4344*38fd1498Szrj       return __result;
4345*38fd1498Szrj     }
4346*38fd1498Szrj 
4347*38fd1498Szrj   /**
4348*38fd1498Szrj    *  @brief Replace each occurrence of one value in a sequence with another
4349*38fd1498Szrj    *         value.
4350*38fd1498Szrj    *  @ingroup mutating_algorithms
4351*38fd1498Szrj    *  @param  __first      A forward iterator.
4352*38fd1498Szrj    *  @param  __last       A forward iterator.
4353*38fd1498Szrj    *  @param  __old_value  The value to be replaced.
4354*38fd1498Szrj    *  @param  __new_value  The replacement value.
4355*38fd1498Szrj    *  @return   replace() returns no value.
4356*38fd1498Szrj    *
4357*38fd1498Szrj    *  For each iterator @c i in the range @p [__first,__last) if @c *i ==
4358*38fd1498Szrj    *  @p __old_value then the assignment @c *i = @p __new_value is performed.
4359*38fd1498Szrj   */
4360*38fd1498Szrj   template<typename _ForwardIterator, typename _Tp>
4361*38fd1498Szrj     void
4362*38fd1498Szrj     replace(_ForwardIterator __first, _ForwardIterator __last,
4363*38fd1498Szrj 	    const _Tp& __old_value, const _Tp& __new_value)
4364*38fd1498Szrj     {
4365*38fd1498Szrj       // concept requirements
4366*38fd1498Szrj       __glibcxx_function_requires(_Mutable_ForwardIteratorConcept<
4367*38fd1498Szrj 				  _ForwardIterator>)
4368*38fd1498Szrj       __glibcxx_function_requires(_EqualOpConcept<
4369*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type, _Tp>)
4370*38fd1498Szrj       __glibcxx_function_requires(_ConvertibleConcept<_Tp,
4371*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
4372*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4373*38fd1498Szrj 
4374*38fd1498Szrj       for (; __first != __last; ++__first)
4375*38fd1498Szrj 	if (*__first == __old_value)
4376*38fd1498Szrj 	  *__first = __new_value;
4377*38fd1498Szrj     }
4378*38fd1498Szrj 
4379*38fd1498Szrj   /**
4380*38fd1498Szrj    *  @brief Replace each value in a sequence for which a predicate returns
4381*38fd1498Szrj    *         true with another value.
4382*38fd1498Szrj    *  @ingroup mutating_algorithms
4383*38fd1498Szrj    *  @param  __first      A forward iterator.
4384*38fd1498Szrj    *  @param  __last       A forward iterator.
4385*38fd1498Szrj    *  @param  __pred       A predicate.
4386*38fd1498Szrj    *  @param  __new_value  The replacement value.
4387*38fd1498Szrj    *  @return   replace_if() returns no value.
4388*38fd1498Szrj    *
4389*38fd1498Szrj    *  For each iterator @c i in the range @p [__first,__last) if @p __pred(*i)
4390*38fd1498Szrj    *  is true then the assignment @c *i = @p __new_value is performed.
4391*38fd1498Szrj   */
4392*38fd1498Szrj   template<typename _ForwardIterator, typename _Predicate, typename _Tp>
4393*38fd1498Szrj     void
4394*38fd1498Szrj     replace_if(_ForwardIterator __first, _ForwardIterator __last,
4395*38fd1498Szrj 	       _Predicate __pred, const _Tp& __new_value)
4396*38fd1498Szrj     {
4397*38fd1498Szrj       // concept requirements
4398*38fd1498Szrj       __glibcxx_function_requires(_Mutable_ForwardIteratorConcept<
4399*38fd1498Szrj 				  _ForwardIterator>)
4400*38fd1498Szrj       __glibcxx_function_requires(_ConvertibleConcept<_Tp,
4401*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
4402*38fd1498Szrj       __glibcxx_function_requires(_UnaryPredicateConcept<_Predicate,
4403*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
4404*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4405*38fd1498Szrj 
4406*38fd1498Szrj       for (; __first != __last; ++__first)
4407*38fd1498Szrj 	if (__pred(*__first))
4408*38fd1498Szrj 	  *__first = __new_value;
4409*38fd1498Szrj     }
4410*38fd1498Szrj 
4411*38fd1498Szrj   /**
4412*38fd1498Szrj    *  @brief Assign the result of a function object to each value in a
4413*38fd1498Szrj    *         sequence.
4414*38fd1498Szrj    *  @ingroup mutating_algorithms
4415*38fd1498Szrj    *  @param  __first  A forward iterator.
4416*38fd1498Szrj    *  @param  __last   A forward iterator.
4417*38fd1498Szrj    *  @param  __gen    A function object taking no arguments and returning
4418*38fd1498Szrj    *                 std::iterator_traits<_ForwardIterator>::value_type
4419*38fd1498Szrj    *  @return   generate() returns no value.
4420*38fd1498Szrj    *
4421*38fd1498Szrj    *  Performs the assignment @c *i = @p __gen() for each @c i in the range
4422*38fd1498Szrj    *  @p [__first,__last).
4423*38fd1498Szrj   */
4424*38fd1498Szrj   template<typename _ForwardIterator, typename _Generator>
4425*38fd1498Szrj     void
4426*38fd1498Szrj     generate(_ForwardIterator __first, _ForwardIterator __last,
4427*38fd1498Szrj 	     _Generator __gen)
4428*38fd1498Szrj     {
4429*38fd1498Szrj       // concept requirements
4430*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
4431*38fd1498Szrj       __glibcxx_function_requires(_GeneratorConcept<_Generator,
4432*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
4433*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4434*38fd1498Szrj 
4435*38fd1498Szrj       for (; __first != __last; ++__first)
4436*38fd1498Szrj 	*__first = __gen();
4437*38fd1498Szrj     }
4438*38fd1498Szrj 
4439*38fd1498Szrj   /**
4440*38fd1498Szrj    *  @brief Assign the result of a function object to each value in a
4441*38fd1498Szrj    *         sequence.
4442*38fd1498Szrj    *  @ingroup mutating_algorithms
4443*38fd1498Szrj    *  @param  __first  A forward iterator.
4444*38fd1498Szrj    *  @param  __n      The length of the sequence.
4445*38fd1498Szrj    *  @param  __gen    A function object taking no arguments and returning
4446*38fd1498Szrj    *                 std::iterator_traits<_ForwardIterator>::value_type
4447*38fd1498Szrj    *  @return   The end of the sequence, @p __first+__n
4448*38fd1498Szrj    *
4449*38fd1498Szrj    *  Performs the assignment @c *i = @p __gen() for each @c i in the range
4450*38fd1498Szrj    *  @p [__first,__first+__n).
4451*38fd1498Szrj    *
4452*38fd1498Szrj    *  _GLIBCXX_RESOLVE_LIB_DEFECTS
4453*38fd1498Szrj    *  DR 865. More algorithms that throw away information
4454*38fd1498Szrj   */
4455*38fd1498Szrj   template<typename _OutputIterator, typename _Size, typename _Generator>
4456*38fd1498Szrj     _OutputIterator
4457*38fd1498Szrj     generate_n(_OutputIterator __first, _Size __n, _Generator __gen)
4458*38fd1498Szrj     {
4459*38fd1498Szrj       // concept requirements
4460*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
4461*38fd1498Szrj 	    // "the type returned by a _Generator"
4462*38fd1498Szrj 	    __typeof__(__gen())>)
4463*38fd1498Szrj 
4464*38fd1498Szrj       for (__decltype(__n + 0) __niter = __n;
4465*38fd1498Szrj 	   __niter > 0; --__niter, (void) ++__first)
4466*38fd1498Szrj 	*__first = __gen();
4467*38fd1498Szrj       return __first;
4468*38fd1498Szrj     }
4469*38fd1498Szrj 
4470*38fd1498Szrj   /**
4471*38fd1498Szrj    *  @brief Copy a sequence, removing consecutive duplicate values.
4472*38fd1498Szrj    *  @ingroup mutating_algorithms
4473*38fd1498Szrj    *  @param  __first   An input iterator.
4474*38fd1498Szrj    *  @param  __last    An input iterator.
4475*38fd1498Szrj    *  @param  __result  An output iterator.
4476*38fd1498Szrj    *  @return   An iterator designating the end of the resulting sequence.
4477*38fd1498Szrj    *
4478*38fd1498Szrj    *  Copies each element in the range @p [__first,__last) to the range
4479*38fd1498Szrj    *  beginning at @p __result, except that only the first element is copied
4480*38fd1498Szrj    *  from groups of consecutive elements that compare equal.
4481*38fd1498Szrj    *  unique_copy() is stable, so the relative order of elements that are
4482*38fd1498Szrj    *  copied is unchanged.
4483*38fd1498Szrj    *
4484*38fd1498Szrj    *  _GLIBCXX_RESOLVE_LIB_DEFECTS
4485*38fd1498Szrj    *  DR 241. Does unique_copy() require CopyConstructible and Assignable?
4486*38fd1498Szrj    *
4487*38fd1498Szrj    *  _GLIBCXX_RESOLVE_LIB_DEFECTS
4488*38fd1498Szrj    *  DR 538. 241 again: Does unique_copy() require CopyConstructible and
4489*38fd1498Szrj    *  Assignable?
4490*38fd1498Szrj   */
4491*38fd1498Szrj   template<typename _InputIterator, typename _OutputIterator>
4492*38fd1498Szrj     inline _OutputIterator
4493*38fd1498Szrj     unique_copy(_InputIterator __first, _InputIterator __last,
4494*38fd1498Szrj 		_OutputIterator __result)
4495*38fd1498Szrj     {
4496*38fd1498Szrj       // concept requirements
4497*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
4498*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
4499*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
4500*38fd1498Szrj       __glibcxx_function_requires(_EqualityComparableConcept<
4501*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
4502*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4503*38fd1498Szrj 
4504*38fd1498Szrj       if (__first == __last)
4505*38fd1498Szrj 	return __result;
4506*38fd1498Szrj       return std::__unique_copy(__first, __last, __result,
4507*38fd1498Szrj 				__gnu_cxx::__ops::__iter_equal_to_iter(),
4508*38fd1498Szrj 				std::__iterator_category(__first),
4509*38fd1498Szrj 				std::__iterator_category(__result));
4510*38fd1498Szrj     }
4511*38fd1498Szrj 
4512*38fd1498Szrj   /**
4513*38fd1498Szrj    *  @brief Copy a sequence, removing consecutive values using a predicate.
4514*38fd1498Szrj    *  @ingroup mutating_algorithms
4515*38fd1498Szrj    *  @param  __first        An input iterator.
4516*38fd1498Szrj    *  @param  __last         An input iterator.
4517*38fd1498Szrj    *  @param  __result       An output iterator.
4518*38fd1498Szrj    *  @param  __binary_pred  A binary predicate.
4519*38fd1498Szrj    *  @return   An iterator designating the end of the resulting sequence.
4520*38fd1498Szrj    *
4521*38fd1498Szrj    *  Copies each element in the range @p [__first,__last) to the range
4522*38fd1498Szrj    *  beginning at @p __result, except that only the first element is copied
4523*38fd1498Szrj    *  from groups of consecutive elements for which @p __binary_pred returns
4524*38fd1498Szrj    *  true.
4525*38fd1498Szrj    *  unique_copy() is stable, so the relative order of elements that are
4526*38fd1498Szrj    *  copied is unchanged.
4527*38fd1498Szrj    *
4528*38fd1498Szrj    *  _GLIBCXX_RESOLVE_LIB_DEFECTS
4529*38fd1498Szrj    *  DR 241. Does unique_copy() require CopyConstructible and Assignable?
4530*38fd1498Szrj   */
4531*38fd1498Szrj   template<typename _InputIterator, typename _OutputIterator,
4532*38fd1498Szrj 	   typename _BinaryPredicate>
4533*38fd1498Szrj     inline _OutputIterator
4534*38fd1498Szrj     unique_copy(_InputIterator __first, _InputIterator __last,
4535*38fd1498Szrj 		_OutputIterator __result,
4536*38fd1498Szrj 		_BinaryPredicate __binary_pred)
4537*38fd1498Szrj     {
4538*38fd1498Szrj       // concept requirements -- predicates checked later
4539*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator>)
4540*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
4541*38fd1498Szrj 	    typename iterator_traits<_InputIterator>::value_type>)
4542*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4543*38fd1498Szrj 
4544*38fd1498Szrj       if (__first == __last)
4545*38fd1498Szrj 	return __result;
4546*38fd1498Szrj       return std::__unique_copy(__first, __last, __result,
4547*38fd1498Szrj 			__gnu_cxx::__ops::__iter_comp_iter(__binary_pred),
4548*38fd1498Szrj 				std::__iterator_category(__first),
4549*38fd1498Szrj 				std::__iterator_category(__result));
4550*38fd1498Szrj     }
4551*38fd1498Szrj 
4552*38fd1498Szrj #if _GLIBCXX_HOSTED
4553*38fd1498Szrj   /**
4554*38fd1498Szrj    *  @brief Randomly shuffle the elements of a sequence.
4555*38fd1498Szrj    *  @ingroup mutating_algorithms
4556*38fd1498Szrj    *  @param  __first   A forward iterator.
4557*38fd1498Szrj    *  @param  __last    A forward iterator.
4558*38fd1498Szrj    *  @return  Nothing.
4559*38fd1498Szrj    *
4560*38fd1498Szrj    *  Reorder the elements in the range @p [__first,__last) using a random
4561*38fd1498Szrj    *  distribution, so that every possible ordering of the sequence is
4562*38fd1498Szrj    *  equally likely.
4563*38fd1498Szrj   */
4564*38fd1498Szrj   template<typename _RandomAccessIterator>
4565*38fd1498Szrj     inline void
4566*38fd1498Szrj     random_shuffle(_RandomAccessIterator __first, _RandomAccessIterator __last)
4567*38fd1498Szrj     {
4568*38fd1498Szrj       // concept requirements
4569*38fd1498Szrj       __glibcxx_function_requires(_Mutable_RandomAccessIteratorConcept<
4570*38fd1498Szrj 	    _RandomAccessIterator>)
4571*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4572*38fd1498Szrj 
4573*38fd1498Szrj       if (__first != __last)
4574*38fd1498Szrj 	for (_RandomAccessIterator __i = __first + 1; __i != __last; ++__i)
4575*38fd1498Szrj 	  {
4576*38fd1498Szrj 	    // XXX rand() % N is not uniformly distributed
4577*38fd1498Szrj 	    _RandomAccessIterator __j = __first
4578*38fd1498Szrj 					+ std::rand() % ((__i - __first) + 1);
4579*38fd1498Szrj 	    if (__i != __j)
4580*38fd1498Szrj 	      std::iter_swap(__i, __j);
4581*38fd1498Szrj 	  }
4582*38fd1498Szrj     }
4583*38fd1498Szrj #endif
4584*38fd1498Szrj 
4585*38fd1498Szrj   /**
4586*38fd1498Szrj    *  @brief Shuffle the elements of a sequence using a random number
4587*38fd1498Szrj    *         generator.
4588*38fd1498Szrj    *  @ingroup mutating_algorithms
4589*38fd1498Szrj    *  @param  __first   A forward iterator.
4590*38fd1498Szrj    *  @param  __last    A forward iterator.
4591*38fd1498Szrj    *  @param  __rand    The RNG functor or function.
4592*38fd1498Szrj    *  @return  Nothing.
4593*38fd1498Szrj    *
4594*38fd1498Szrj    *  Reorders the elements in the range @p [__first,__last) using @p __rand to
4595*38fd1498Szrj    *  provide a random distribution. Calling @p __rand(N) for a positive
4596*38fd1498Szrj    *  integer @p N should return a randomly chosen integer from the
4597*38fd1498Szrj    *  range [0,N).
4598*38fd1498Szrj   */
4599*38fd1498Szrj   template<typename _RandomAccessIterator, typename _RandomNumberGenerator>
4600*38fd1498Szrj     void
4601*38fd1498Szrj     random_shuffle(_RandomAccessIterator __first, _RandomAccessIterator __last,
4602*38fd1498Szrj #if __cplusplus >= 201103L
4603*38fd1498Szrj 		   _RandomNumberGenerator&& __rand)
4604*38fd1498Szrj #else
4605*38fd1498Szrj 		   _RandomNumberGenerator& __rand)
4606*38fd1498Szrj #endif
4607*38fd1498Szrj     {
4608*38fd1498Szrj       // concept requirements
4609*38fd1498Szrj       __glibcxx_function_requires(_Mutable_RandomAccessIteratorConcept<
4610*38fd1498Szrj 	    _RandomAccessIterator>)
4611*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4612*38fd1498Szrj 
4613*38fd1498Szrj       if (__first == __last)
4614*38fd1498Szrj 	return;
4615*38fd1498Szrj       for (_RandomAccessIterator __i = __first + 1; __i != __last; ++__i)
4616*38fd1498Szrj 	{
4617*38fd1498Szrj 	  _RandomAccessIterator __j = __first + __rand((__i - __first) + 1);
4618*38fd1498Szrj 	  if (__i != __j)
4619*38fd1498Szrj 	    std::iter_swap(__i, __j);
4620*38fd1498Szrj 	}
4621*38fd1498Szrj     }
4622*38fd1498Szrj 
4623*38fd1498Szrj 
4624*38fd1498Szrj   /**
4625*38fd1498Szrj    *  @brief Move elements for which a predicate is true to the beginning
4626*38fd1498Szrj    *         of a sequence.
4627*38fd1498Szrj    *  @ingroup mutating_algorithms
4628*38fd1498Szrj    *  @param  __first   A forward iterator.
4629*38fd1498Szrj    *  @param  __last    A forward iterator.
4630*38fd1498Szrj    *  @param  __pred    A predicate functor.
4631*38fd1498Szrj    *  @return  An iterator @p middle such that @p __pred(i) is true for each
4632*38fd1498Szrj    *  iterator @p i in the range @p [__first,middle) and false for each @p i
4633*38fd1498Szrj    *  in the range @p [middle,__last).
4634*38fd1498Szrj    *
4635*38fd1498Szrj    *  @p __pred must not modify its operand. @p partition() does not preserve
4636*38fd1498Szrj    *  the relative ordering of elements in each group, use
4637*38fd1498Szrj    *  @p stable_partition() if this is needed.
4638*38fd1498Szrj   */
4639*38fd1498Szrj   template<typename _ForwardIterator, typename _Predicate>
4640*38fd1498Szrj     inline _ForwardIterator
4641*38fd1498Szrj     partition(_ForwardIterator __first, _ForwardIterator __last,
4642*38fd1498Szrj 	      _Predicate   __pred)
4643*38fd1498Szrj     {
4644*38fd1498Szrj       // concept requirements
4645*38fd1498Szrj       __glibcxx_function_requires(_Mutable_ForwardIteratorConcept<
4646*38fd1498Szrj 				  _ForwardIterator>)
4647*38fd1498Szrj       __glibcxx_function_requires(_UnaryPredicateConcept<_Predicate,
4648*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
4649*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4650*38fd1498Szrj 
4651*38fd1498Szrj       return std::__partition(__first, __last, __pred,
4652*38fd1498Szrj 			      std::__iterator_category(__first));
4653*38fd1498Szrj     }
4654*38fd1498Szrj 
4655*38fd1498Szrj 
4656*38fd1498Szrj   /**
4657*38fd1498Szrj    *  @brief Sort the smallest elements of a sequence.
4658*38fd1498Szrj    *  @ingroup sorting_algorithms
4659*38fd1498Szrj    *  @param  __first   An iterator.
4660*38fd1498Szrj    *  @param  __middle  Another iterator.
4661*38fd1498Szrj    *  @param  __last    Another iterator.
4662*38fd1498Szrj    *  @return  Nothing.
4663*38fd1498Szrj    *
4664*38fd1498Szrj    *  Sorts the smallest @p (__middle-__first) elements in the range
4665*38fd1498Szrj    *  @p [first,last) and moves them to the range @p [__first,__middle). The
4666*38fd1498Szrj    *  order of the remaining elements in the range @p [__middle,__last) is
4667*38fd1498Szrj    *  undefined.
4668*38fd1498Szrj    *  After the sort if @e i and @e j are iterators in the range
4669*38fd1498Szrj    *  @p [__first,__middle) such that i precedes j and @e k is an iterator in
4670*38fd1498Szrj    *  the range @p [__middle,__last) then *j<*i and *k<*i are both false.
4671*38fd1498Szrj   */
4672*38fd1498Szrj   template<typename _RandomAccessIterator>
4673*38fd1498Szrj     inline void
4674*38fd1498Szrj     partial_sort(_RandomAccessIterator __first,
4675*38fd1498Szrj 		 _RandomAccessIterator __middle,
4676*38fd1498Szrj 		 _RandomAccessIterator __last)
4677*38fd1498Szrj     {
4678*38fd1498Szrj       // concept requirements
4679*38fd1498Szrj       __glibcxx_function_requires(_Mutable_RandomAccessIteratorConcept<
4680*38fd1498Szrj 	    _RandomAccessIterator>)
4681*38fd1498Szrj       __glibcxx_function_requires(_LessThanComparableConcept<
4682*38fd1498Szrj 	    typename iterator_traits<_RandomAccessIterator>::value_type>)
4683*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __middle);
4684*38fd1498Szrj       __glibcxx_requires_valid_range(__middle, __last);
4685*38fd1498Szrj       __glibcxx_requires_irreflexive(__first, __last);
4686*38fd1498Szrj 
4687*38fd1498Szrj       std::__partial_sort(__first, __middle, __last,
4688*38fd1498Szrj 			  __gnu_cxx::__ops::__iter_less_iter());
4689*38fd1498Szrj     }
4690*38fd1498Szrj 
4691*38fd1498Szrj   /**
4692*38fd1498Szrj    *  @brief Sort the smallest elements of a sequence using a predicate
4693*38fd1498Szrj    *         for comparison.
4694*38fd1498Szrj    *  @ingroup sorting_algorithms
4695*38fd1498Szrj    *  @param  __first   An iterator.
4696*38fd1498Szrj    *  @param  __middle  Another iterator.
4697*38fd1498Szrj    *  @param  __last    Another iterator.
4698*38fd1498Szrj    *  @param  __comp    A comparison functor.
4699*38fd1498Szrj    *  @return  Nothing.
4700*38fd1498Szrj    *
4701*38fd1498Szrj    *  Sorts the smallest @p (__middle-__first) elements in the range
4702*38fd1498Szrj    *  @p [__first,__last) and moves them to the range @p [__first,__middle). The
4703*38fd1498Szrj    *  order of the remaining elements in the range @p [__middle,__last) is
4704*38fd1498Szrj    *  undefined.
4705*38fd1498Szrj    *  After the sort if @e i and @e j are iterators in the range
4706*38fd1498Szrj    *  @p [__first,__middle) such that i precedes j and @e k is an iterator in
4707*38fd1498Szrj    *  the range @p [__middle,__last) then @p *__comp(j,*i) and @p __comp(*k,*i)
4708*38fd1498Szrj    *  are both false.
4709*38fd1498Szrj   */
4710*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
4711*38fd1498Szrj     inline void
4712*38fd1498Szrj     partial_sort(_RandomAccessIterator __first,
4713*38fd1498Szrj 		 _RandomAccessIterator __middle,
4714*38fd1498Szrj 		 _RandomAccessIterator __last,
4715*38fd1498Szrj 		 _Compare __comp)
4716*38fd1498Szrj     {
4717*38fd1498Szrj       // concept requirements
4718*38fd1498Szrj       __glibcxx_function_requires(_Mutable_RandomAccessIteratorConcept<
4719*38fd1498Szrj 	    _RandomAccessIterator>)
4720*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
4721*38fd1498Szrj 	    typename iterator_traits<_RandomAccessIterator>::value_type,
4722*38fd1498Szrj 	    typename iterator_traits<_RandomAccessIterator>::value_type>)
4723*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __middle);
4724*38fd1498Szrj       __glibcxx_requires_valid_range(__middle, __last);
4725*38fd1498Szrj       __glibcxx_requires_irreflexive_pred(__first, __last, __comp);
4726*38fd1498Szrj 
4727*38fd1498Szrj       std::__partial_sort(__first, __middle, __last,
4728*38fd1498Szrj 			  __gnu_cxx::__ops::__iter_comp_iter(__comp));
4729*38fd1498Szrj     }
4730*38fd1498Szrj 
4731*38fd1498Szrj   /**
4732*38fd1498Szrj    *  @brief Sort a sequence just enough to find a particular position.
4733*38fd1498Szrj    *  @ingroup sorting_algorithms
4734*38fd1498Szrj    *  @param  __first   An iterator.
4735*38fd1498Szrj    *  @param  __nth     Another iterator.
4736*38fd1498Szrj    *  @param  __last    Another iterator.
4737*38fd1498Szrj    *  @return  Nothing.
4738*38fd1498Szrj    *
4739*38fd1498Szrj    *  Rearranges the elements in the range @p [__first,__last) so that @p *__nth
4740*38fd1498Szrj    *  is the same element that would have been in that position had the
4741*38fd1498Szrj    *  whole sequence been sorted. The elements either side of @p *__nth are
4742*38fd1498Szrj    *  not completely sorted, but for any iterator @e i in the range
4743*38fd1498Szrj    *  @p [__first,__nth) and any iterator @e j in the range @p [__nth,__last) it
4744*38fd1498Szrj    *  holds that *j < *i is false.
4745*38fd1498Szrj   */
4746*38fd1498Szrj   template<typename _RandomAccessIterator>
4747*38fd1498Szrj     inline void
4748*38fd1498Szrj     nth_element(_RandomAccessIterator __first, _RandomAccessIterator __nth,
4749*38fd1498Szrj 		_RandomAccessIterator __last)
4750*38fd1498Szrj     {
4751*38fd1498Szrj       // concept requirements
4752*38fd1498Szrj       __glibcxx_function_requires(_Mutable_RandomAccessIteratorConcept<
4753*38fd1498Szrj 				  _RandomAccessIterator>)
4754*38fd1498Szrj       __glibcxx_function_requires(_LessThanComparableConcept<
4755*38fd1498Szrj 	    typename iterator_traits<_RandomAccessIterator>::value_type>)
4756*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __nth);
4757*38fd1498Szrj       __glibcxx_requires_valid_range(__nth, __last);
4758*38fd1498Szrj       __glibcxx_requires_irreflexive(__first, __last);
4759*38fd1498Szrj 
4760*38fd1498Szrj       if (__first == __last || __nth == __last)
4761*38fd1498Szrj 	return;
4762*38fd1498Szrj 
4763*38fd1498Szrj       std::__introselect(__first, __nth, __last,
4764*38fd1498Szrj 			 std::__lg(__last - __first) * 2,
4765*38fd1498Szrj 			 __gnu_cxx::__ops::__iter_less_iter());
4766*38fd1498Szrj     }
4767*38fd1498Szrj 
4768*38fd1498Szrj   /**
4769*38fd1498Szrj    *  @brief Sort a sequence just enough to find a particular position
4770*38fd1498Szrj    *         using a predicate for comparison.
4771*38fd1498Szrj    *  @ingroup sorting_algorithms
4772*38fd1498Szrj    *  @param  __first   An iterator.
4773*38fd1498Szrj    *  @param  __nth     Another iterator.
4774*38fd1498Szrj    *  @param  __last    Another iterator.
4775*38fd1498Szrj    *  @param  __comp    A comparison functor.
4776*38fd1498Szrj    *  @return  Nothing.
4777*38fd1498Szrj    *
4778*38fd1498Szrj    *  Rearranges the elements in the range @p [__first,__last) so that @p *__nth
4779*38fd1498Szrj    *  is the same element that would have been in that position had the
4780*38fd1498Szrj    *  whole sequence been sorted. The elements either side of @p *__nth are
4781*38fd1498Szrj    *  not completely sorted, but for any iterator @e i in the range
4782*38fd1498Szrj    *  @p [__first,__nth) and any iterator @e j in the range @p [__nth,__last) it
4783*38fd1498Szrj    *  holds that @p __comp(*j,*i) is false.
4784*38fd1498Szrj   */
4785*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
4786*38fd1498Szrj     inline void
4787*38fd1498Szrj     nth_element(_RandomAccessIterator __first, _RandomAccessIterator __nth,
4788*38fd1498Szrj 		_RandomAccessIterator __last, _Compare __comp)
4789*38fd1498Szrj     {
4790*38fd1498Szrj       // concept requirements
4791*38fd1498Szrj       __glibcxx_function_requires(_Mutable_RandomAccessIteratorConcept<
4792*38fd1498Szrj 				  _RandomAccessIterator>)
4793*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
4794*38fd1498Szrj 	    typename iterator_traits<_RandomAccessIterator>::value_type,
4795*38fd1498Szrj 	    typename iterator_traits<_RandomAccessIterator>::value_type>)
4796*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __nth);
4797*38fd1498Szrj       __glibcxx_requires_valid_range(__nth, __last);
4798*38fd1498Szrj       __glibcxx_requires_irreflexive_pred(__first, __last, __comp);
4799*38fd1498Szrj 
4800*38fd1498Szrj       if (__first == __last || __nth == __last)
4801*38fd1498Szrj 	return;
4802*38fd1498Szrj 
4803*38fd1498Szrj       std::__introselect(__first, __nth, __last,
4804*38fd1498Szrj 			 std::__lg(__last - __first) * 2,
4805*38fd1498Szrj 			 __gnu_cxx::__ops::__iter_comp_iter(__comp));
4806*38fd1498Szrj     }
4807*38fd1498Szrj 
4808*38fd1498Szrj   /**
4809*38fd1498Szrj    *  @brief Sort the elements of a sequence.
4810*38fd1498Szrj    *  @ingroup sorting_algorithms
4811*38fd1498Szrj    *  @param  __first   An iterator.
4812*38fd1498Szrj    *  @param  __last    Another iterator.
4813*38fd1498Szrj    *  @return  Nothing.
4814*38fd1498Szrj    *
4815*38fd1498Szrj    *  Sorts the elements in the range @p [__first,__last) in ascending order,
4816*38fd1498Szrj    *  such that for each iterator @e i in the range @p [__first,__last-1),
4817*38fd1498Szrj    *  *(i+1)<*i is false.
4818*38fd1498Szrj    *
4819*38fd1498Szrj    *  The relative ordering of equivalent elements is not preserved, use
4820*38fd1498Szrj    *  @p stable_sort() if this is needed.
4821*38fd1498Szrj   */
4822*38fd1498Szrj   template<typename _RandomAccessIterator>
4823*38fd1498Szrj     inline void
4824*38fd1498Szrj     sort(_RandomAccessIterator __first, _RandomAccessIterator __last)
4825*38fd1498Szrj     {
4826*38fd1498Szrj       // concept requirements
4827*38fd1498Szrj       __glibcxx_function_requires(_Mutable_RandomAccessIteratorConcept<
4828*38fd1498Szrj 	    _RandomAccessIterator>)
4829*38fd1498Szrj       __glibcxx_function_requires(_LessThanComparableConcept<
4830*38fd1498Szrj 	    typename iterator_traits<_RandomAccessIterator>::value_type>)
4831*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4832*38fd1498Szrj       __glibcxx_requires_irreflexive(__first, __last);
4833*38fd1498Szrj 
4834*38fd1498Szrj       std::__sort(__first, __last, __gnu_cxx::__ops::__iter_less_iter());
4835*38fd1498Szrj     }
4836*38fd1498Szrj 
4837*38fd1498Szrj   /**
4838*38fd1498Szrj    *  @brief Sort the elements of a sequence using a predicate for comparison.
4839*38fd1498Szrj    *  @ingroup sorting_algorithms
4840*38fd1498Szrj    *  @param  __first   An iterator.
4841*38fd1498Szrj    *  @param  __last    Another iterator.
4842*38fd1498Szrj    *  @param  __comp    A comparison functor.
4843*38fd1498Szrj    *  @return  Nothing.
4844*38fd1498Szrj    *
4845*38fd1498Szrj    *  Sorts the elements in the range @p [__first,__last) in ascending order,
4846*38fd1498Szrj    *  such that @p __comp(*(i+1),*i) is false for every iterator @e i in the
4847*38fd1498Szrj    *  range @p [__first,__last-1).
4848*38fd1498Szrj    *
4849*38fd1498Szrj    *  The relative ordering of equivalent elements is not preserved, use
4850*38fd1498Szrj    *  @p stable_sort() if this is needed.
4851*38fd1498Szrj   */
4852*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
4853*38fd1498Szrj     inline void
4854*38fd1498Szrj     sort(_RandomAccessIterator __first, _RandomAccessIterator __last,
4855*38fd1498Szrj 	 _Compare __comp)
4856*38fd1498Szrj     {
4857*38fd1498Szrj       // concept requirements
4858*38fd1498Szrj       __glibcxx_function_requires(_Mutable_RandomAccessIteratorConcept<
4859*38fd1498Szrj 	    _RandomAccessIterator>)
4860*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
4861*38fd1498Szrj 	    typename iterator_traits<_RandomAccessIterator>::value_type,
4862*38fd1498Szrj 	    typename iterator_traits<_RandomAccessIterator>::value_type>)
4863*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
4864*38fd1498Szrj       __glibcxx_requires_irreflexive_pred(__first, __last, __comp);
4865*38fd1498Szrj 
4866*38fd1498Szrj       std::__sort(__first, __last, __gnu_cxx::__ops::__iter_comp_iter(__comp));
4867*38fd1498Szrj     }
4868*38fd1498Szrj 
4869*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
4870*38fd1498Szrj 	   typename _OutputIterator, typename _Compare>
4871*38fd1498Szrj     _OutputIterator
4872*38fd1498Szrj     __merge(_InputIterator1 __first1, _InputIterator1 __last1,
4873*38fd1498Szrj 	    _InputIterator2 __first2, _InputIterator2 __last2,
4874*38fd1498Szrj 	    _OutputIterator __result, _Compare __comp)
4875*38fd1498Szrj     {
4876*38fd1498Szrj       while (__first1 != __last1 && __first2 != __last2)
4877*38fd1498Szrj 	{
4878*38fd1498Szrj 	  if (__comp(__first2, __first1))
4879*38fd1498Szrj 	    {
4880*38fd1498Szrj 	      *__result = *__first2;
4881*38fd1498Szrj 	      ++__first2;
4882*38fd1498Szrj 	    }
4883*38fd1498Szrj 	  else
4884*38fd1498Szrj 	    {
4885*38fd1498Szrj 	      *__result = *__first1;
4886*38fd1498Szrj 	      ++__first1;
4887*38fd1498Szrj 	    }
4888*38fd1498Szrj 	  ++__result;
4889*38fd1498Szrj 	}
4890*38fd1498Szrj       return std::copy(__first2, __last2,
4891*38fd1498Szrj 		       std::copy(__first1, __last1, __result));
4892*38fd1498Szrj     }
4893*38fd1498Szrj 
4894*38fd1498Szrj   /**
4895*38fd1498Szrj    *  @brief Merges two sorted ranges.
4896*38fd1498Szrj    *  @ingroup sorting_algorithms
4897*38fd1498Szrj    *  @param  __first1  An iterator.
4898*38fd1498Szrj    *  @param  __first2  Another iterator.
4899*38fd1498Szrj    *  @param  __last1   Another iterator.
4900*38fd1498Szrj    *  @param  __last2   Another iterator.
4901*38fd1498Szrj    *  @param  __result  An iterator pointing to the end of the merged range.
4902*38fd1498Szrj    *  @return         An iterator pointing to the first element <em>not less
4903*38fd1498Szrj    *                  than</em> @e val.
4904*38fd1498Szrj    *
4905*38fd1498Szrj    *  Merges the ranges @p [__first1,__last1) and @p [__first2,__last2) into
4906*38fd1498Szrj    *  the sorted range @p [__result, __result + (__last1-__first1) +
4907*38fd1498Szrj    *  (__last2-__first2)).  Both input ranges must be sorted, and the
4908*38fd1498Szrj    *  output range must not overlap with either of the input ranges.
4909*38fd1498Szrj    *  The sort is @e stable, that is, for equivalent elements in the
4910*38fd1498Szrj    *  two ranges, elements from the first range will always come
4911*38fd1498Szrj    *  before elements from the second.
4912*38fd1498Szrj   */
4913*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
4914*38fd1498Szrj 	   typename _OutputIterator>
4915*38fd1498Szrj     inline _OutputIterator
4916*38fd1498Szrj     merge(_InputIterator1 __first1, _InputIterator1 __last1,
4917*38fd1498Szrj 	  _InputIterator2 __first2, _InputIterator2 __last2,
4918*38fd1498Szrj 	  _OutputIterator __result)
4919*38fd1498Szrj     {
4920*38fd1498Szrj       // concept requirements
4921*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator1>)
4922*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator2>)
4923*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
4924*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
4925*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
4926*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
4927*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
4928*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type,
4929*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
4930*38fd1498Szrj       __glibcxx_requires_sorted_set(__first1, __last1, __first2);
4931*38fd1498Szrj       __glibcxx_requires_sorted_set(__first2, __last2, __first1);
4932*38fd1498Szrj       __glibcxx_requires_irreflexive2(__first1, __last1);
4933*38fd1498Szrj       __glibcxx_requires_irreflexive2(__first2, __last2);
4934*38fd1498Szrj 
4935*38fd1498Szrj       return _GLIBCXX_STD_A::__merge(__first1, __last1,
4936*38fd1498Szrj 				     __first2, __last2, __result,
4937*38fd1498Szrj 				     __gnu_cxx::__ops::__iter_less_iter());
4938*38fd1498Szrj     }
4939*38fd1498Szrj 
4940*38fd1498Szrj   /**
4941*38fd1498Szrj    *  @brief Merges two sorted ranges.
4942*38fd1498Szrj    *  @ingroup sorting_algorithms
4943*38fd1498Szrj    *  @param  __first1  An iterator.
4944*38fd1498Szrj    *  @param  __first2  Another iterator.
4945*38fd1498Szrj    *  @param  __last1   Another iterator.
4946*38fd1498Szrj    *  @param  __last2   Another iterator.
4947*38fd1498Szrj    *  @param  __result  An iterator pointing to the end of the merged range.
4948*38fd1498Szrj    *  @param  __comp    A functor to use for comparisons.
4949*38fd1498Szrj    *  @return         An iterator pointing to the first element "not less
4950*38fd1498Szrj    *                  than" @e val.
4951*38fd1498Szrj    *
4952*38fd1498Szrj    *  Merges the ranges @p [__first1,__last1) and @p [__first2,__last2) into
4953*38fd1498Szrj    *  the sorted range @p [__result, __result + (__last1-__first1) +
4954*38fd1498Szrj    *  (__last2-__first2)).  Both input ranges must be sorted, and the
4955*38fd1498Szrj    *  output range must not overlap with either of the input ranges.
4956*38fd1498Szrj    *  The sort is @e stable, that is, for equivalent elements in the
4957*38fd1498Szrj    *  two ranges, elements from the first range will always come
4958*38fd1498Szrj    *  before elements from the second.
4959*38fd1498Szrj    *
4960*38fd1498Szrj    *  The comparison function should have the same effects on ordering as
4961*38fd1498Szrj    *  the function used for the initial sort.
4962*38fd1498Szrj   */
4963*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
4964*38fd1498Szrj 	   typename _OutputIterator, typename _Compare>
4965*38fd1498Szrj     inline _OutputIterator
4966*38fd1498Szrj     merge(_InputIterator1 __first1, _InputIterator1 __last1,
4967*38fd1498Szrj 	  _InputIterator2 __first2, _InputIterator2 __last2,
4968*38fd1498Szrj 	  _OutputIterator __result, _Compare __comp)
4969*38fd1498Szrj     {
4970*38fd1498Szrj       // concept requirements
4971*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator1>)
4972*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator2>)
4973*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
4974*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
4975*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
4976*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
4977*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
4978*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type,
4979*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
4980*38fd1498Szrj       __glibcxx_requires_sorted_set_pred(__first1, __last1, __first2, __comp);
4981*38fd1498Szrj       __glibcxx_requires_sorted_set_pred(__first2, __last2, __first1, __comp);
4982*38fd1498Szrj       __glibcxx_requires_irreflexive_pred2(__first1, __last1, __comp);
4983*38fd1498Szrj       __glibcxx_requires_irreflexive_pred2(__first2, __last2, __comp);
4984*38fd1498Szrj 
4985*38fd1498Szrj       return _GLIBCXX_STD_A::__merge(__first1, __last1,
4986*38fd1498Szrj 				__first2, __last2, __result,
4987*38fd1498Szrj 				__gnu_cxx::__ops::__iter_comp_iter(__comp));
4988*38fd1498Szrj     }
4989*38fd1498Szrj 
4990*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
4991*38fd1498Szrj     inline void
4992*38fd1498Szrj     __stable_sort(_RandomAccessIterator __first, _RandomAccessIterator __last,
4993*38fd1498Szrj 		  _Compare __comp)
4994*38fd1498Szrj     {
4995*38fd1498Szrj       typedef typename iterator_traits<_RandomAccessIterator>::value_type
4996*38fd1498Szrj 	_ValueType;
4997*38fd1498Szrj       typedef typename iterator_traits<_RandomAccessIterator>::difference_type
4998*38fd1498Szrj 	_DistanceType;
4999*38fd1498Szrj 
5000*38fd1498Szrj       typedef _Temporary_buffer<_RandomAccessIterator, _ValueType> _TmpBuf;
5001*38fd1498Szrj       _TmpBuf __buf(__first, __last);
5002*38fd1498Szrj 
5003*38fd1498Szrj       if (__buf.begin() == 0)
5004*38fd1498Szrj 	std::__inplace_stable_sort(__first, __last, __comp);
5005*38fd1498Szrj       else
5006*38fd1498Szrj 	std::__stable_sort_adaptive(__first, __last, __buf.begin(),
5007*38fd1498Szrj 				    _DistanceType(__buf.size()), __comp);
5008*38fd1498Szrj     }
5009*38fd1498Szrj 
5010*38fd1498Szrj   /**
5011*38fd1498Szrj    *  @brief Sort the elements of a sequence, preserving the relative order
5012*38fd1498Szrj    *         of equivalent elements.
5013*38fd1498Szrj    *  @ingroup sorting_algorithms
5014*38fd1498Szrj    *  @param  __first   An iterator.
5015*38fd1498Szrj    *  @param  __last    Another iterator.
5016*38fd1498Szrj    *  @return  Nothing.
5017*38fd1498Szrj    *
5018*38fd1498Szrj    *  Sorts the elements in the range @p [__first,__last) in ascending order,
5019*38fd1498Szrj    *  such that for each iterator @p i in the range @p [__first,__last-1),
5020*38fd1498Szrj    *  @p *(i+1)<*i is false.
5021*38fd1498Szrj    *
5022*38fd1498Szrj    *  The relative ordering of equivalent elements is preserved, so any two
5023*38fd1498Szrj    *  elements @p x and @p y in the range @p [__first,__last) such that
5024*38fd1498Szrj    *  @p x<y is false and @p y<x is false will have the same relative
5025*38fd1498Szrj    *  ordering after calling @p stable_sort().
5026*38fd1498Szrj   */
5027*38fd1498Szrj   template<typename _RandomAccessIterator>
5028*38fd1498Szrj     inline void
5029*38fd1498Szrj     stable_sort(_RandomAccessIterator __first, _RandomAccessIterator __last)
5030*38fd1498Szrj     {
5031*38fd1498Szrj       // concept requirements
5032*38fd1498Szrj       __glibcxx_function_requires(_Mutable_RandomAccessIteratorConcept<
5033*38fd1498Szrj 	    _RandomAccessIterator>)
5034*38fd1498Szrj       __glibcxx_function_requires(_LessThanComparableConcept<
5035*38fd1498Szrj 	    typename iterator_traits<_RandomAccessIterator>::value_type>)
5036*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
5037*38fd1498Szrj       __glibcxx_requires_irreflexive(__first, __last);
5038*38fd1498Szrj 
5039*38fd1498Szrj       _GLIBCXX_STD_A::__stable_sort(__first, __last,
5040*38fd1498Szrj 				    __gnu_cxx::__ops::__iter_less_iter());
5041*38fd1498Szrj     }
5042*38fd1498Szrj 
5043*38fd1498Szrj   /**
5044*38fd1498Szrj    *  @brief Sort the elements of a sequence using a predicate for comparison,
5045*38fd1498Szrj    *         preserving the relative order of equivalent elements.
5046*38fd1498Szrj    *  @ingroup sorting_algorithms
5047*38fd1498Szrj    *  @param  __first   An iterator.
5048*38fd1498Szrj    *  @param  __last    Another iterator.
5049*38fd1498Szrj    *  @param  __comp    A comparison functor.
5050*38fd1498Szrj    *  @return  Nothing.
5051*38fd1498Szrj    *
5052*38fd1498Szrj    *  Sorts the elements in the range @p [__first,__last) in ascending order,
5053*38fd1498Szrj    *  such that for each iterator @p i in the range @p [__first,__last-1),
5054*38fd1498Szrj    *  @p __comp(*(i+1),*i) is false.
5055*38fd1498Szrj    *
5056*38fd1498Szrj    *  The relative ordering of equivalent elements is preserved, so any two
5057*38fd1498Szrj    *  elements @p x and @p y in the range @p [__first,__last) such that
5058*38fd1498Szrj    *  @p __comp(x,y) is false and @p __comp(y,x) is false will have the same
5059*38fd1498Szrj    *  relative ordering after calling @p stable_sort().
5060*38fd1498Szrj   */
5061*38fd1498Szrj   template<typename _RandomAccessIterator, typename _Compare>
5062*38fd1498Szrj     inline void
5063*38fd1498Szrj     stable_sort(_RandomAccessIterator __first, _RandomAccessIterator __last,
5064*38fd1498Szrj 		_Compare __comp)
5065*38fd1498Szrj     {
5066*38fd1498Szrj       // concept requirements
5067*38fd1498Szrj       __glibcxx_function_requires(_Mutable_RandomAccessIteratorConcept<
5068*38fd1498Szrj 	    _RandomAccessIterator>)
5069*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
5070*38fd1498Szrj 	    typename iterator_traits<_RandomAccessIterator>::value_type,
5071*38fd1498Szrj 	    typename iterator_traits<_RandomAccessIterator>::value_type>)
5072*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
5073*38fd1498Szrj       __glibcxx_requires_irreflexive_pred(__first, __last, __comp);
5074*38fd1498Szrj 
5075*38fd1498Szrj       _GLIBCXX_STD_A::__stable_sort(__first, __last,
5076*38fd1498Szrj 				    __gnu_cxx::__ops::__iter_comp_iter(__comp));
5077*38fd1498Szrj     }
5078*38fd1498Szrj 
5079*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
5080*38fd1498Szrj 	   typename _OutputIterator,
5081*38fd1498Szrj 	   typename _Compare>
5082*38fd1498Szrj     _OutputIterator
5083*38fd1498Szrj     __set_union(_InputIterator1 __first1, _InputIterator1 __last1,
5084*38fd1498Szrj 		_InputIterator2 __first2, _InputIterator2 __last2,
5085*38fd1498Szrj 		_OutputIterator __result, _Compare __comp)
5086*38fd1498Szrj     {
5087*38fd1498Szrj       while (__first1 != __last1 && __first2 != __last2)
5088*38fd1498Szrj 	{
5089*38fd1498Szrj 	  if (__comp(__first1, __first2))
5090*38fd1498Szrj 	    {
5091*38fd1498Szrj 	      *__result = *__first1;
5092*38fd1498Szrj 	      ++__first1;
5093*38fd1498Szrj 	    }
5094*38fd1498Szrj 	  else if (__comp(__first2, __first1))
5095*38fd1498Szrj 	    {
5096*38fd1498Szrj 	      *__result = *__first2;
5097*38fd1498Szrj 	      ++__first2;
5098*38fd1498Szrj 	    }
5099*38fd1498Szrj 	  else
5100*38fd1498Szrj 	    {
5101*38fd1498Szrj 	      *__result = *__first1;
5102*38fd1498Szrj 	      ++__first1;
5103*38fd1498Szrj 	      ++__first2;
5104*38fd1498Szrj 	    }
5105*38fd1498Szrj 	  ++__result;
5106*38fd1498Szrj 	}
5107*38fd1498Szrj       return std::copy(__first2, __last2,
5108*38fd1498Szrj 		       std::copy(__first1, __last1, __result));
5109*38fd1498Szrj     }
5110*38fd1498Szrj 
5111*38fd1498Szrj   /**
5112*38fd1498Szrj    *  @brief Return the union of two sorted ranges.
5113*38fd1498Szrj    *  @ingroup set_algorithms
5114*38fd1498Szrj    *  @param  __first1  Start of first range.
5115*38fd1498Szrj    *  @param  __last1   End of first range.
5116*38fd1498Szrj    *  @param  __first2  Start of second range.
5117*38fd1498Szrj    *  @param  __last2   End of second range.
5118*38fd1498Szrj    *  @param  __result  Start of output range.
5119*38fd1498Szrj    *  @return  End of the output range.
5120*38fd1498Szrj    *  @ingroup set_algorithms
5121*38fd1498Szrj    *
5122*38fd1498Szrj    *  This operation iterates over both ranges, copying elements present in
5123*38fd1498Szrj    *  each range in order to the output range.  Iterators increment for each
5124*38fd1498Szrj    *  range.  When the current element of one range is less than the other,
5125*38fd1498Szrj    *  that element is copied and the iterator advanced.  If an element is
5126*38fd1498Szrj    *  contained in both ranges, the element from the first range is copied and
5127*38fd1498Szrj    *  both ranges advance.  The output range may not overlap either input
5128*38fd1498Szrj    *  range.
5129*38fd1498Szrj   */
5130*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
5131*38fd1498Szrj 	   typename _OutputIterator>
5132*38fd1498Szrj     inline _OutputIterator
5133*38fd1498Szrj     set_union(_InputIterator1 __first1, _InputIterator1 __last1,
5134*38fd1498Szrj 	      _InputIterator2 __first2, _InputIterator2 __last2,
5135*38fd1498Szrj 	      _OutputIterator __result)
5136*38fd1498Szrj     {
5137*38fd1498Szrj       // concept requirements
5138*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator1>)
5139*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator2>)
5140*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
5141*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5142*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
5143*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
5144*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
5145*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type,
5146*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
5147*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
5148*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type,
5149*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5150*38fd1498Szrj       __glibcxx_requires_sorted_set(__first1, __last1, __first2);
5151*38fd1498Szrj       __glibcxx_requires_sorted_set(__first2, __last2, __first1);
5152*38fd1498Szrj       __glibcxx_requires_irreflexive2(__first1, __last1);
5153*38fd1498Szrj       __glibcxx_requires_irreflexive2(__first2, __last2);
5154*38fd1498Szrj 
5155*38fd1498Szrj       return _GLIBCXX_STD_A::__set_union(__first1, __last1,
5156*38fd1498Szrj 				__first2, __last2, __result,
5157*38fd1498Szrj 				__gnu_cxx::__ops::__iter_less_iter());
5158*38fd1498Szrj     }
5159*38fd1498Szrj 
5160*38fd1498Szrj   /**
5161*38fd1498Szrj    *  @brief Return the union of two sorted ranges using a comparison functor.
5162*38fd1498Szrj    *  @ingroup set_algorithms
5163*38fd1498Szrj    *  @param  __first1  Start of first range.
5164*38fd1498Szrj    *  @param  __last1   End of first range.
5165*38fd1498Szrj    *  @param  __first2  Start of second range.
5166*38fd1498Szrj    *  @param  __last2   End of second range.
5167*38fd1498Szrj    *  @param  __result  Start of output range.
5168*38fd1498Szrj    *  @param  __comp    The comparison functor.
5169*38fd1498Szrj    *  @return  End of the output range.
5170*38fd1498Szrj    *  @ingroup set_algorithms
5171*38fd1498Szrj    *
5172*38fd1498Szrj    *  This operation iterates over both ranges, copying elements present in
5173*38fd1498Szrj    *  each range in order to the output range.  Iterators increment for each
5174*38fd1498Szrj    *  range.  When the current element of one range is less than the other
5175*38fd1498Szrj    *  according to @p __comp, that element is copied and the iterator advanced.
5176*38fd1498Szrj    *  If an equivalent element according to @p __comp is contained in both
5177*38fd1498Szrj    *  ranges, the element from the first range is copied and both ranges
5178*38fd1498Szrj    *  advance.  The output range may not overlap either input range.
5179*38fd1498Szrj   */
5180*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
5181*38fd1498Szrj 	   typename _OutputIterator, typename _Compare>
5182*38fd1498Szrj     inline _OutputIterator
5183*38fd1498Szrj     set_union(_InputIterator1 __first1, _InputIterator1 __last1,
5184*38fd1498Szrj 	      _InputIterator2 __first2, _InputIterator2 __last2,
5185*38fd1498Szrj 	      _OutputIterator __result, _Compare __comp)
5186*38fd1498Szrj     {
5187*38fd1498Szrj       // concept requirements
5188*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator1>)
5189*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator2>)
5190*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
5191*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5192*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
5193*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
5194*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
5195*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type,
5196*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
5197*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
5198*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type,
5199*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5200*38fd1498Szrj       __glibcxx_requires_sorted_set_pred(__first1, __last1, __first2, __comp);
5201*38fd1498Szrj       __glibcxx_requires_sorted_set_pred(__first2, __last2, __first1, __comp);
5202*38fd1498Szrj       __glibcxx_requires_irreflexive_pred2(__first1, __last1, __comp);
5203*38fd1498Szrj       __glibcxx_requires_irreflexive_pred2(__first2, __last2, __comp);
5204*38fd1498Szrj 
5205*38fd1498Szrj       return _GLIBCXX_STD_A::__set_union(__first1, __last1,
5206*38fd1498Szrj 				__first2, __last2, __result,
5207*38fd1498Szrj 				__gnu_cxx::__ops::__iter_comp_iter(__comp));
5208*38fd1498Szrj     }
5209*38fd1498Szrj 
5210*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
5211*38fd1498Szrj 	   typename _OutputIterator,
5212*38fd1498Szrj 	   typename _Compare>
5213*38fd1498Szrj     _OutputIterator
5214*38fd1498Szrj     __set_intersection(_InputIterator1 __first1, _InputIterator1 __last1,
5215*38fd1498Szrj 		       _InputIterator2 __first2, _InputIterator2 __last2,
5216*38fd1498Szrj 		       _OutputIterator __result, _Compare __comp)
5217*38fd1498Szrj     {
5218*38fd1498Szrj       while (__first1 != __last1 && __first2 != __last2)
5219*38fd1498Szrj 	if (__comp(__first1, __first2))
5220*38fd1498Szrj 	  ++__first1;
5221*38fd1498Szrj 	else if (__comp(__first2, __first1))
5222*38fd1498Szrj 	  ++__first2;
5223*38fd1498Szrj 	else
5224*38fd1498Szrj 	  {
5225*38fd1498Szrj 	    *__result = *__first1;
5226*38fd1498Szrj 	    ++__first1;
5227*38fd1498Szrj 	    ++__first2;
5228*38fd1498Szrj 	    ++__result;
5229*38fd1498Szrj 	  }
5230*38fd1498Szrj       return __result;
5231*38fd1498Szrj     }
5232*38fd1498Szrj 
5233*38fd1498Szrj   /**
5234*38fd1498Szrj    *  @brief Return the intersection of two sorted ranges.
5235*38fd1498Szrj    *  @ingroup set_algorithms
5236*38fd1498Szrj    *  @param  __first1  Start of first range.
5237*38fd1498Szrj    *  @param  __last1   End of first range.
5238*38fd1498Szrj    *  @param  __first2  Start of second range.
5239*38fd1498Szrj    *  @param  __last2   End of second range.
5240*38fd1498Szrj    *  @param  __result  Start of output range.
5241*38fd1498Szrj    *  @return  End of the output range.
5242*38fd1498Szrj    *  @ingroup set_algorithms
5243*38fd1498Szrj    *
5244*38fd1498Szrj    *  This operation iterates over both ranges, copying elements present in
5245*38fd1498Szrj    *  both ranges in order to the output range.  Iterators increment for each
5246*38fd1498Szrj    *  range.  When the current element of one range is less than the other,
5247*38fd1498Szrj    *  that iterator advances.  If an element is contained in both ranges, the
5248*38fd1498Szrj    *  element from the first range is copied and both ranges advance.  The
5249*38fd1498Szrj    *  output range may not overlap either input range.
5250*38fd1498Szrj   */
5251*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
5252*38fd1498Szrj 	   typename _OutputIterator>
5253*38fd1498Szrj     inline _OutputIterator
5254*38fd1498Szrj     set_intersection(_InputIterator1 __first1, _InputIterator1 __last1,
5255*38fd1498Szrj 		     _InputIterator2 __first2, _InputIterator2 __last2,
5256*38fd1498Szrj 		     _OutputIterator __result)
5257*38fd1498Szrj     {
5258*38fd1498Szrj       // concept requirements
5259*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator1>)
5260*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator2>)
5261*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
5262*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5263*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
5264*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type,
5265*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
5266*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
5267*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type,
5268*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5269*38fd1498Szrj       __glibcxx_requires_sorted_set(__first1, __last1, __first2);
5270*38fd1498Szrj       __glibcxx_requires_sorted_set(__first2, __last2, __first1);
5271*38fd1498Szrj       __glibcxx_requires_irreflexive2(__first1, __last1);
5272*38fd1498Szrj       __glibcxx_requires_irreflexive2(__first2, __last2);
5273*38fd1498Szrj 
5274*38fd1498Szrj       return _GLIBCXX_STD_A::__set_intersection(__first1, __last1,
5275*38fd1498Szrj 				     __first2, __last2, __result,
5276*38fd1498Szrj 				     __gnu_cxx::__ops::__iter_less_iter());
5277*38fd1498Szrj     }
5278*38fd1498Szrj 
5279*38fd1498Szrj   /**
5280*38fd1498Szrj    *  @brief Return the intersection of two sorted ranges using comparison
5281*38fd1498Szrj    *  functor.
5282*38fd1498Szrj    *  @ingroup set_algorithms
5283*38fd1498Szrj    *  @param  __first1  Start of first range.
5284*38fd1498Szrj    *  @param  __last1   End of first range.
5285*38fd1498Szrj    *  @param  __first2  Start of second range.
5286*38fd1498Szrj    *  @param  __last2   End of second range.
5287*38fd1498Szrj    *  @param  __result  Start of output range.
5288*38fd1498Szrj    *  @param  __comp    The comparison functor.
5289*38fd1498Szrj    *  @return  End of the output range.
5290*38fd1498Szrj    *  @ingroup set_algorithms
5291*38fd1498Szrj    *
5292*38fd1498Szrj    *  This operation iterates over both ranges, copying elements present in
5293*38fd1498Szrj    *  both ranges in order to the output range.  Iterators increment for each
5294*38fd1498Szrj    *  range.  When the current element of one range is less than the other
5295*38fd1498Szrj    *  according to @p __comp, that iterator advances.  If an element is
5296*38fd1498Szrj    *  contained in both ranges according to @p __comp, the element from the
5297*38fd1498Szrj    *  first range is copied and both ranges advance.  The output range may not
5298*38fd1498Szrj    *  overlap either input range.
5299*38fd1498Szrj   */
5300*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
5301*38fd1498Szrj 	   typename _OutputIterator, typename _Compare>
5302*38fd1498Szrj     inline _OutputIterator
5303*38fd1498Szrj     set_intersection(_InputIterator1 __first1, _InputIterator1 __last1,
5304*38fd1498Szrj 		     _InputIterator2 __first2, _InputIterator2 __last2,
5305*38fd1498Szrj 		     _OutputIterator __result, _Compare __comp)
5306*38fd1498Szrj     {
5307*38fd1498Szrj       // concept requirements
5308*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator1>)
5309*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator2>)
5310*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
5311*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5312*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
5313*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type,
5314*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
5315*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
5316*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type,
5317*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5318*38fd1498Szrj       __glibcxx_requires_sorted_set_pred(__first1, __last1, __first2, __comp);
5319*38fd1498Szrj       __glibcxx_requires_sorted_set_pred(__first2, __last2, __first1, __comp);
5320*38fd1498Szrj       __glibcxx_requires_irreflexive_pred2(__first1, __last1, __comp);
5321*38fd1498Szrj       __glibcxx_requires_irreflexive_pred2(__first2, __last2, __comp);
5322*38fd1498Szrj 
5323*38fd1498Szrj       return _GLIBCXX_STD_A::__set_intersection(__first1, __last1,
5324*38fd1498Szrj 				__first2, __last2, __result,
5325*38fd1498Szrj 				__gnu_cxx::__ops::__iter_comp_iter(__comp));
5326*38fd1498Szrj     }
5327*38fd1498Szrj 
5328*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
5329*38fd1498Szrj 	   typename _OutputIterator,
5330*38fd1498Szrj 	   typename _Compare>
5331*38fd1498Szrj     _OutputIterator
5332*38fd1498Szrj     __set_difference(_InputIterator1 __first1, _InputIterator1 __last1,
5333*38fd1498Szrj 		     _InputIterator2 __first2, _InputIterator2 __last2,
5334*38fd1498Szrj 		     _OutputIterator __result, _Compare __comp)
5335*38fd1498Szrj     {
5336*38fd1498Szrj       while (__first1 != __last1 && __first2 != __last2)
5337*38fd1498Szrj 	if (__comp(__first1, __first2))
5338*38fd1498Szrj 	  {
5339*38fd1498Szrj 	    *__result = *__first1;
5340*38fd1498Szrj 	    ++__first1;
5341*38fd1498Szrj 	    ++__result;
5342*38fd1498Szrj 	  }
5343*38fd1498Szrj 	else if (__comp(__first2, __first1))
5344*38fd1498Szrj 	  ++__first2;
5345*38fd1498Szrj 	else
5346*38fd1498Szrj 	  {
5347*38fd1498Szrj 	    ++__first1;
5348*38fd1498Szrj 	    ++__first2;
5349*38fd1498Szrj 	  }
5350*38fd1498Szrj       return std::copy(__first1, __last1, __result);
5351*38fd1498Szrj     }
5352*38fd1498Szrj 
5353*38fd1498Szrj   /**
5354*38fd1498Szrj    *  @brief Return the difference of two sorted ranges.
5355*38fd1498Szrj    *  @ingroup set_algorithms
5356*38fd1498Szrj    *  @param  __first1  Start of first range.
5357*38fd1498Szrj    *  @param  __last1   End of first range.
5358*38fd1498Szrj    *  @param  __first2  Start of second range.
5359*38fd1498Szrj    *  @param  __last2   End of second range.
5360*38fd1498Szrj    *  @param  __result  Start of output range.
5361*38fd1498Szrj    *  @return  End of the output range.
5362*38fd1498Szrj    *  @ingroup set_algorithms
5363*38fd1498Szrj    *
5364*38fd1498Szrj    *  This operation iterates over both ranges, copying elements present in
5365*38fd1498Szrj    *  the first range but not the second in order to the output range.
5366*38fd1498Szrj    *  Iterators increment for each range.  When the current element of the
5367*38fd1498Szrj    *  first range is less than the second, that element is copied and the
5368*38fd1498Szrj    *  iterator advances.  If the current element of the second range is less,
5369*38fd1498Szrj    *  the iterator advances, but no element is copied.  If an element is
5370*38fd1498Szrj    *  contained in both ranges, no elements are copied and both ranges
5371*38fd1498Szrj    *  advance.  The output range may not overlap either input range.
5372*38fd1498Szrj   */
5373*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
5374*38fd1498Szrj 	   typename _OutputIterator>
5375*38fd1498Szrj     inline _OutputIterator
5376*38fd1498Szrj     set_difference(_InputIterator1 __first1, _InputIterator1 __last1,
5377*38fd1498Szrj 		   _InputIterator2 __first2, _InputIterator2 __last2,
5378*38fd1498Szrj 		   _OutputIterator __result)
5379*38fd1498Szrj     {
5380*38fd1498Szrj       // concept requirements
5381*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator1>)
5382*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator2>)
5383*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
5384*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5385*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
5386*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type,
5387*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
5388*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
5389*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type,
5390*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5391*38fd1498Szrj       __glibcxx_requires_sorted_set(__first1, __last1, __first2);
5392*38fd1498Szrj       __glibcxx_requires_sorted_set(__first2, __last2, __first1);
5393*38fd1498Szrj       __glibcxx_requires_irreflexive2(__first1, __last1);
5394*38fd1498Szrj       __glibcxx_requires_irreflexive2(__first2, __last2);
5395*38fd1498Szrj 
5396*38fd1498Szrj       return _GLIBCXX_STD_A::__set_difference(__first1, __last1,
5397*38fd1498Szrj 				   __first2, __last2, __result,
5398*38fd1498Szrj 				   __gnu_cxx::__ops::__iter_less_iter());
5399*38fd1498Szrj     }
5400*38fd1498Szrj 
5401*38fd1498Szrj   /**
5402*38fd1498Szrj    *  @brief  Return the difference of two sorted ranges using comparison
5403*38fd1498Szrj    *  functor.
5404*38fd1498Szrj    *  @ingroup set_algorithms
5405*38fd1498Szrj    *  @param  __first1  Start of first range.
5406*38fd1498Szrj    *  @param  __last1   End of first range.
5407*38fd1498Szrj    *  @param  __first2  Start of second range.
5408*38fd1498Szrj    *  @param  __last2   End of second range.
5409*38fd1498Szrj    *  @param  __result  Start of output range.
5410*38fd1498Szrj    *  @param  __comp    The comparison functor.
5411*38fd1498Szrj    *  @return  End of the output range.
5412*38fd1498Szrj    *  @ingroup set_algorithms
5413*38fd1498Szrj    *
5414*38fd1498Szrj    *  This operation iterates over both ranges, copying elements present in
5415*38fd1498Szrj    *  the first range but not the second in order to the output range.
5416*38fd1498Szrj    *  Iterators increment for each range.  When the current element of the
5417*38fd1498Szrj    *  first range is less than the second according to @p __comp, that element
5418*38fd1498Szrj    *  is copied and the iterator advances.  If the current element of the
5419*38fd1498Szrj    *  second range is less, no element is copied and the iterator advances.
5420*38fd1498Szrj    *  If an element is contained in both ranges according to @p __comp, no
5421*38fd1498Szrj    *  elements are copied and both ranges advance.  The output range may not
5422*38fd1498Szrj    *  overlap either input range.
5423*38fd1498Szrj   */
5424*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
5425*38fd1498Szrj 	   typename _OutputIterator, typename _Compare>
5426*38fd1498Szrj     inline _OutputIterator
5427*38fd1498Szrj     set_difference(_InputIterator1 __first1, _InputIterator1 __last1,
5428*38fd1498Szrj 		   _InputIterator2 __first2, _InputIterator2 __last2,
5429*38fd1498Szrj 		   _OutputIterator __result, _Compare __comp)
5430*38fd1498Szrj     {
5431*38fd1498Szrj       // concept requirements
5432*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator1>)
5433*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator2>)
5434*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
5435*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5436*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
5437*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type,
5438*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
5439*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
5440*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type,
5441*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5442*38fd1498Szrj       __glibcxx_requires_sorted_set_pred(__first1, __last1, __first2, __comp);
5443*38fd1498Szrj       __glibcxx_requires_sorted_set_pred(__first2, __last2, __first1, __comp);
5444*38fd1498Szrj       __glibcxx_requires_irreflexive_pred2(__first1, __last1, __comp);
5445*38fd1498Szrj       __glibcxx_requires_irreflexive_pred2(__first2, __last2, __comp);
5446*38fd1498Szrj 
5447*38fd1498Szrj       return _GLIBCXX_STD_A::__set_difference(__first1, __last1,
5448*38fd1498Szrj 				   __first2, __last2, __result,
5449*38fd1498Szrj 				   __gnu_cxx::__ops::__iter_comp_iter(__comp));
5450*38fd1498Szrj     }
5451*38fd1498Szrj 
5452*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
5453*38fd1498Szrj 	   typename _OutputIterator,
5454*38fd1498Szrj 	   typename _Compare>
5455*38fd1498Szrj     _OutputIterator
5456*38fd1498Szrj     __set_symmetric_difference(_InputIterator1 __first1,
5457*38fd1498Szrj 			       _InputIterator1 __last1,
5458*38fd1498Szrj 			       _InputIterator2 __first2,
5459*38fd1498Szrj 			       _InputIterator2 __last2,
5460*38fd1498Szrj 			       _OutputIterator __result,
5461*38fd1498Szrj 			       _Compare __comp)
5462*38fd1498Szrj     {
5463*38fd1498Szrj       while (__first1 != __last1 && __first2 != __last2)
5464*38fd1498Szrj 	if (__comp(__first1, __first2))
5465*38fd1498Szrj 	  {
5466*38fd1498Szrj 	    *__result = *__first1;
5467*38fd1498Szrj 	    ++__first1;
5468*38fd1498Szrj 	    ++__result;
5469*38fd1498Szrj 	  }
5470*38fd1498Szrj 	else if (__comp(__first2, __first1))
5471*38fd1498Szrj 	  {
5472*38fd1498Szrj 	    *__result = *__first2;
5473*38fd1498Szrj 	    ++__first2;
5474*38fd1498Szrj 	    ++__result;
5475*38fd1498Szrj 	  }
5476*38fd1498Szrj 	else
5477*38fd1498Szrj 	  {
5478*38fd1498Szrj 	    ++__first1;
5479*38fd1498Szrj 	    ++__first2;
5480*38fd1498Szrj 	  }
5481*38fd1498Szrj       return std::copy(__first2, __last2,
5482*38fd1498Szrj 		       std::copy(__first1, __last1, __result));
5483*38fd1498Szrj     }
5484*38fd1498Szrj 
5485*38fd1498Szrj   /**
5486*38fd1498Szrj    *  @brief  Return the symmetric difference of two sorted ranges.
5487*38fd1498Szrj    *  @ingroup set_algorithms
5488*38fd1498Szrj    *  @param  __first1  Start of first range.
5489*38fd1498Szrj    *  @param  __last1   End of first range.
5490*38fd1498Szrj    *  @param  __first2  Start of second range.
5491*38fd1498Szrj    *  @param  __last2   End of second range.
5492*38fd1498Szrj    *  @param  __result  Start of output range.
5493*38fd1498Szrj    *  @return  End of the output range.
5494*38fd1498Szrj    *  @ingroup set_algorithms
5495*38fd1498Szrj    *
5496*38fd1498Szrj    *  This operation iterates over both ranges, copying elements present in
5497*38fd1498Szrj    *  one range but not the other in order to the output range.  Iterators
5498*38fd1498Szrj    *  increment for each range.  When the current element of one range is less
5499*38fd1498Szrj    *  than the other, that element is copied and the iterator advances.  If an
5500*38fd1498Szrj    *  element is contained in both ranges, no elements are copied and both
5501*38fd1498Szrj    *  ranges advance.  The output range may not overlap either input range.
5502*38fd1498Szrj   */
5503*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
5504*38fd1498Szrj 	   typename _OutputIterator>
5505*38fd1498Szrj     inline _OutputIterator
5506*38fd1498Szrj     set_symmetric_difference(_InputIterator1 __first1, _InputIterator1 __last1,
5507*38fd1498Szrj 			     _InputIterator2 __first2, _InputIterator2 __last2,
5508*38fd1498Szrj 			     _OutputIterator __result)
5509*38fd1498Szrj     {
5510*38fd1498Szrj       // concept requirements
5511*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator1>)
5512*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator2>)
5513*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
5514*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5515*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
5516*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
5517*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
5518*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type,
5519*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
5520*38fd1498Szrj       __glibcxx_function_requires(_LessThanOpConcept<
5521*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type,
5522*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5523*38fd1498Szrj       __glibcxx_requires_sorted_set(__first1, __last1, __first2);
5524*38fd1498Szrj       __glibcxx_requires_sorted_set(__first2, __last2, __first1);
5525*38fd1498Szrj       __glibcxx_requires_irreflexive2(__first1, __last1);
5526*38fd1498Szrj       __glibcxx_requires_irreflexive2(__first2, __last2);
5527*38fd1498Szrj 
5528*38fd1498Szrj       return _GLIBCXX_STD_A::__set_symmetric_difference(__first1, __last1,
5529*38fd1498Szrj 					__first2, __last2, __result,
5530*38fd1498Szrj 					__gnu_cxx::__ops::__iter_less_iter());
5531*38fd1498Szrj     }
5532*38fd1498Szrj 
5533*38fd1498Szrj   /**
5534*38fd1498Szrj    *  @brief  Return the symmetric difference of two sorted ranges using
5535*38fd1498Szrj    *  comparison functor.
5536*38fd1498Szrj    *  @ingroup set_algorithms
5537*38fd1498Szrj    *  @param  __first1  Start of first range.
5538*38fd1498Szrj    *  @param  __last1   End of first range.
5539*38fd1498Szrj    *  @param  __first2  Start of second range.
5540*38fd1498Szrj    *  @param  __last2   End of second range.
5541*38fd1498Szrj    *  @param  __result  Start of output range.
5542*38fd1498Szrj    *  @param  __comp    The comparison functor.
5543*38fd1498Szrj    *  @return  End of the output range.
5544*38fd1498Szrj    *  @ingroup set_algorithms
5545*38fd1498Szrj    *
5546*38fd1498Szrj    *  This operation iterates over both ranges, copying elements present in
5547*38fd1498Szrj    *  one range but not the other in order to the output range.  Iterators
5548*38fd1498Szrj    *  increment for each range.  When the current element of one range is less
5549*38fd1498Szrj    *  than the other according to @p comp, that element is copied and the
5550*38fd1498Szrj    *  iterator advances.  If an element is contained in both ranges according
5551*38fd1498Szrj    *  to @p __comp, no elements are copied and both ranges advance.  The output
5552*38fd1498Szrj    *  range may not overlap either input range.
5553*38fd1498Szrj   */
5554*38fd1498Szrj   template<typename _InputIterator1, typename _InputIterator2,
5555*38fd1498Szrj 	   typename _OutputIterator, typename _Compare>
5556*38fd1498Szrj     inline _OutputIterator
5557*38fd1498Szrj     set_symmetric_difference(_InputIterator1 __first1, _InputIterator1 __last1,
5558*38fd1498Szrj 			     _InputIterator2 __first2, _InputIterator2 __last2,
5559*38fd1498Szrj 			     _OutputIterator __result,
5560*38fd1498Szrj 			     _Compare __comp)
5561*38fd1498Szrj     {
5562*38fd1498Szrj       // concept requirements
5563*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator1>)
5564*38fd1498Szrj       __glibcxx_function_requires(_InputIteratorConcept<_InputIterator2>)
5565*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
5566*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5567*38fd1498Szrj       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator,
5568*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
5569*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
5570*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type,
5571*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type>)
5572*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
5573*38fd1498Szrj 	    typename iterator_traits<_InputIterator2>::value_type,
5574*38fd1498Szrj 	    typename iterator_traits<_InputIterator1>::value_type>)
5575*38fd1498Szrj       __glibcxx_requires_sorted_set_pred(__first1, __last1, __first2, __comp);
5576*38fd1498Szrj       __glibcxx_requires_sorted_set_pred(__first2, __last2, __first1, __comp);
5577*38fd1498Szrj       __glibcxx_requires_irreflexive_pred2(__first1, __last1, __comp);
5578*38fd1498Szrj       __glibcxx_requires_irreflexive_pred2(__first2, __last2, __comp);
5579*38fd1498Szrj 
5580*38fd1498Szrj       return _GLIBCXX_STD_A::__set_symmetric_difference(__first1, __last1,
5581*38fd1498Szrj 				__first2, __last2, __result,
5582*38fd1498Szrj 				__gnu_cxx::__ops::__iter_comp_iter(__comp));
5583*38fd1498Szrj     }
5584*38fd1498Szrj 
5585*38fd1498Szrj   template<typename _ForwardIterator, typename _Compare>
5586*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
5587*38fd1498Szrj     _ForwardIterator
5588*38fd1498Szrj     __min_element(_ForwardIterator __first, _ForwardIterator __last,
5589*38fd1498Szrj 		  _Compare __comp)
5590*38fd1498Szrj     {
5591*38fd1498Szrj       if (__first == __last)
5592*38fd1498Szrj 	return __first;
5593*38fd1498Szrj       _ForwardIterator __result = __first;
5594*38fd1498Szrj       while (++__first != __last)
5595*38fd1498Szrj 	if (__comp(__first, __result))
5596*38fd1498Szrj 	  __result = __first;
5597*38fd1498Szrj       return __result;
5598*38fd1498Szrj     }
5599*38fd1498Szrj 
5600*38fd1498Szrj   /**
5601*38fd1498Szrj    *  @brief  Return the minimum element in a range.
5602*38fd1498Szrj    *  @ingroup sorting_algorithms
5603*38fd1498Szrj    *  @param  __first  Start of range.
5604*38fd1498Szrj    *  @param  __last   End of range.
5605*38fd1498Szrj    *  @return  Iterator referencing the first instance of the smallest value.
5606*38fd1498Szrj   */
5607*38fd1498Szrj   template<typename _ForwardIterator>
5608*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
5609*38fd1498Szrj     _ForwardIterator
5610*38fd1498Szrj     inline min_element(_ForwardIterator __first, _ForwardIterator __last)
5611*38fd1498Szrj     {
5612*38fd1498Szrj       // concept requirements
5613*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
5614*38fd1498Szrj       __glibcxx_function_requires(_LessThanComparableConcept<
5615*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
5616*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
5617*38fd1498Szrj       __glibcxx_requires_irreflexive(__first, __last);
5618*38fd1498Szrj 
5619*38fd1498Szrj       return _GLIBCXX_STD_A::__min_element(__first, __last,
5620*38fd1498Szrj 				__gnu_cxx::__ops::__iter_less_iter());
5621*38fd1498Szrj     }
5622*38fd1498Szrj 
5623*38fd1498Szrj   /**
5624*38fd1498Szrj    *  @brief  Return the minimum element in a range using comparison functor.
5625*38fd1498Szrj    *  @ingroup sorting_algorithms
5626*38fd1498Szrj    *  @param  __first  Start of range.
5627*38fd1498Szrj    *  @param  __last   End of range.
5628*38fd1498Szrj    *  @param  __comp   Comparison functor.
5629*38fd1498Szrj    *  @return  Iterator referencing the first instance of the smallest value
5630*38fd1498Szrj    *  according to __comp.
5631*38fd1498Szrj   */
5632*38fd1498Szrj   template<typename _ForwardIterator, typename _Compare>
5633*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
5634*38fd1498Szrj     inline _ForwardIterator
5635*38fd1498Szrj     min_element(_ForwardIterator __first, _ForwardIterator __last,
5636*38fd1498Szrj 		_Compare __comp)
5637*38fd1498Szrj     {
5638*38fd1498Szrj       // concept requirements
5639*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
5640*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
5641*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type,
5642*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
5643*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
5644*38fd1498Szrj       __glibcxx_requires_irreflexive_pred(__first, __last, __comp);
5645*38fd1498Szrj 
5646*38fd1498Szrj       return _GLIBCXX_STD_A::__min_element(__first, __last,
5647*38fd1498Szrj 				__gnu_cxx::__ops::__iter_comp_iter(__comp));
5648*38fd1498Szrj     }
5649*38fd1498Szrj 
5650*38fd1498Szrj   template<typename _ForwardIterator, typename _Compare>
5651*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
5652*38fd1498Szrj     _ForwardIterator
5653*38fd1498Szrj     __max_element(_ForwardIterator __first, _ForwardIterator __last,
5654*38fd1498Szrj 		  _Compare __comp)
5655*38fd1498Szrj     {
5656*38fd1498Szrj       if (__first == __last) return __first;
5657*38fd1498Szrj       _ForwardIterator __result = __first;
5658*38fd1498Szrj       while (++__first != __last)
5659*38fd1498Szrj 	if (__comp(__result, __first))
5660*38fd1498Szrj 	  __result = __first;
5661*38fd1498Szrj       return __result;
5662*38fd1498Szrj     }
5663*38fd1498Szrj 
5664*38fd1498Szrj   /**
5665*38fd1498Szrj    *  @brief  Return the maximum element in a range.
5666*38fd1498Szrj    *  @ingroup sorting_algorithms
5667*38fd1498Szrj    *  @param  __first  Start of range.
5668*38fd1498Szrj    *  @param  __last   End of range.
5669*38fd1498Szrj    *  @return  Iterator referencing the first instance of the largest value.
5670*38fd1498Szrj   */
5671*38fd1498Szrj   template<typename _ForwardIterator>
5672*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
5673*38fd1498Szrj     inline _ForwardIterator
5674*38fd1498Szrj     max_element(_ForwardIterator __first, _ForwardIterator __last)
5675*38fd1498Szrj     {
5676*38fd1498Szrj       // concept requirements
5677*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
5678*38fd1498Szrj       __glibcxx_function_requires(_LessThanComparableConcept<
5679*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
5680*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
5681*38fd1498Szrj       __glibcxx_requires_irreflexive(__first, __last);
5682*38fd1498Szrj 
5683*38fd1498Szrj       return _GLIBCXX_STD_A::__max_element(__first, __last,
5684*38fd1498Szrj 				__gnu_cxx::__ops::__iter_less_iter());
5685*38fd1498Szrj     }
5686*38fd1498Szrj 
5687*38fd1498Szrj   /**
5688*38fd1498Szrj    *  @brief  Return the maximum element in a range using comparison functor.
5689*38fd1498Szrj    *  @ingroup sorting_algorithms
5690*38fd1498Szrj    *  @param  __first  Start of range.
5691*38fd1498Szrj    *  @param  __last   End of range.
5692*38fd1498Szrj    *  @param  __comp   Comparison functor.
5693*38fd1498Szrj    *  @return  Iterator referencing the first instance of the largest value
5694*38fd1498Szrj    *  according to __comp.
5695*38fd1498Szrj   */
5696*38fd1498Szrj   template<typename _ForwardIterator, typename _Compare>
5697*38fd1498Szrj     _GLIBCXX14_CONSTEXPR
5698*38fd1498Szrj     inline _ForwardIterator
5699*38fd1498Szrj     max_element(_ForwardIterator __first, _ForwardIterator __last,
5700*38fd1498Szrj 		_Compare __comp)
5701*38fd1498Szrj     {
5702*38fd1498Szrj       // concept requirements
5703*38fd1498Szrj       __glibcxx_function_requires(_ForwardIteratorConcept<_ForwardIterator>)
5704*38fd1498Szrj       __glibcxx_function_requires(_BinaryPredicateConcept<_Compare,
5705*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type,
5706*38fd1498Szrj 	    typename iterator_traits<_ForwardIterator>::value_type>)
5707*38fd1498Szrj       __glibcxx_requires_valid_range(__first, __last);
5708*38fd1498Szrj       __glibcxx_requires_irreflexive_pred(__first, __last, __comp);
5709*38fd1498Szrj 
5710*38fd1498Szrj       return _GLIBCXX_STD_A::__max_element(__first, __last,
5711*38fd1498Szrj 				__gnu_cxx::__ops::__iter_comp_iter(__comp));
5712*38fd1498Szrj     }
5713*38fd1498Szrj 
5714*38fd1498Szrj #if __cplusplus >= 201402L
5715*38fd1498Szrj   /// Reservoir sampling algorithm.
5716*38fd1498Szrj   template<typename _InputIterator, typename _RandomAccessIterator,
5717*38fd1498Szrj            typename _Size, typename _UniformRandomBitGenerator>
5718*38fd1498Szrj     _RandomAccessIterator
5719*38fd1498Szrj     __sample(_InputIterator __first, _InputIterator __last, input_iterator_tag,
5720*38fd1498Szrj 	     _RandomAccessIterator __out, random_access_iterator_tag,
5721*38fd1498Szrj 	     _Size __n, _UniformRandomBitGenerator&& __g)
5722*38fd1498Szrj     {
5723*38fd1498Szrj       using __distrib_type = uniform_int_distribution<_Size>;
5724*38fd1498Szrj       using __param_type = typename __distrib_type::param_type;
5725*38fd1498Szrj       __distrib_type __d{};
5726*38fd1498Szrj       _Size __sample_sz = 0;
5727*38fd1498Szrj       while (__first != __last && __sample_sz != __n)
5728*38fd1498Szrj 	{
5729*38fd1498Szrj 	  __out[__sample_sz++] = *__first;
5730*38fd1498Szrj 	  ++__first;
5731*38fd1498Szrj 	}
5732*38fd1498Szrj       for (auto __pop_sz = __sample_sz; __first != __last;
5733*38fd1498Szrj 	  ++__first, (void) ++__pop_sz)
5734*38fd1498Szrj 	{
5735*38fd1498Szrj 	  const auto __k = __d(__g, __param_type{0, __pop_sz});
5736*38fd1498Szrj 	  if (__k < __n)
5737*38fd1498Szrj 	    __out[__k] = *__first;
5738*38fd1498Szrj 	}
5739*38fd1498Szrj       return __out + __sample_sz;
5740*38fd1498Szrj     }
5741*38fd1498Szrj 
5742*38fd1498Szrj   /// Selection sampling algorithm.
5743*38fd1498Szrj   template<typename _ForwardIterator, typename _OutputIterator, typename _Cat,
5744*38fd1498Szrj            typename _Size, typename _UniformRandomBitGenerator>
5745*38fd1498Szrj     _OutputIterator
5746*38fd1498Szrj     __sample(_ForwardIterator __first, _ForwardIterator __last,
5747*38fd1498Szrj 	     forward_iterator_tag,
5748*38fd1498Szrj 	     _OutputIterator __out, _Cat,
5749*38fd1498Szrj 	     _Size __n, _UniformRandomBitGenerator&& __g)
5750*38fd1498Szrj     {
5751*38fd1498Szrj       using __distrib_type = uniform_int_distribution<_Size>;
5752*38fd1498Szrj       using __param_type = typename __distrib_type::param_type;
5753*38fd1498Szrj       using _USize = make_unsigned_t<_Size>;
5754*38fd1498Szrj       using _Gen = remove_reference_t<_UniformRandomBitGenerator>;
5755*38fd1498Szrj       using __uc_type = common_type_t<typename _Gen::result_type, _USize>;
5756*38fd1498Szrj 
5757*38fd1498Szrj       __distrib_type __d{};
5758*38fd1498Szrj       _Size __unsampled_sz = std::distance(__first, __last);
5759*38fd1498Szrj       __n = std::min(__n, __unsampled_sz);
5760*38fd1498Szrj 
5761*38fd1498Szrj       // If possible, we use __gen_two_uniform_ints to efficiently produce
5762*38fd1498Szrj       // two random numbers using a single distribution invocation:
5763*38fd1498Szrj 
5764*38fd1498Szrj       const __uc_type __urngrange = __g.max() - __g.min();
5765*38fd1498Szrj       if (__urngrange / __uc_type(__unsampled_sz) >= __uc_type(__unsampled_sz))
5766*38fd1498Szrj         // I.e. (__urngrange >= __unsampled_sz * __unsampled_sz) but without
5767*38fd1498Szrj 	// wrapping issues.
5768*38fd1498Szrj         {
5769*38fd1498Szrj 	  while (__n != 0 && __unsampled_sz >= 2)
5770*38fd1498Szrj 	    {
5771*38fd1498Szrj 	      const pair<_Size, _Size> __p =
5772*38fd1498Szrj 		__gen_two_uniform_ints(__unsampled_sz, __unsampled_sz - 1, __g);
5773*38fd1498Szrj 
5774*38fd1498Szrj 	      --__unsampled_sz;
5775*38fd1498Szrj 	      if (__p.first < __n)
5776*38fd1498Szrj 		{
5777*38fd1498Szrj 		  *__out++ = *__first;
5778*38fd1498Szrj 		  --__n;
5779*38fd1498Szrj 		}
5780*38fd1498Szrj 
5781*38fd1498Szrj 	      ++__first;
5782*38fd1498Szrj 
5783*38fd1498Szrj 	      if (__n == 0) break;
5784*38fd1498Szrj 
5785*38fd1498Szrj 	      --__unsampled_sz;
5786*38fd1498Szrj 	      if (__p.second < __n)
5787*38fd1498Szrj 		{
5788*38fd1498Szrj 		  *__out++ = *__first;
5789*38fd1498Szrj 		  --__n;
5790*38fd1498Szrj 		}
5791*38fd1498Szrj 
5792*38fd1498Szrj 	      ++__first;
5793*38fd1498Szrj 	    }
5794*38fd1498Szrj         }
5795*38fd1498Szrj 
5796*38fd1498Szrj       // The loop above is otherwise equivalent to this one-at-a-time version:
5797*38fd1498Szrj 
5798*38fd1498Szrj       for (; __n != 0; ++__first)
5799*38fd1498Szrj 	if (__d(__g, __param_type{0, --__unsampled_sz}) < __n)
5800*38fd1498Szrj 	  {
5801*38fd1498Szrj 	    *__out++ = *__first;
5802*38fd1498Szrj 	    --__n;
5803*38fd1498Szrj 	  }
5804*38fd1498Szrj       return __out;
5805*38fd1498Szrj     }
5806*38fd1498Szrj 
5807*38fd1498Szrj #if __cplusplus > 201402L
5808*38fd1498Szrj #define __cpp_lib_sample 201603
5809*38fd1498Szrj   /// Take a random sample from a population.
5810*38fd1498Szrj   template<typename _PopulationIterator, typename _SampleIterator,
5811*38fd1498Szrj            typename _Distance, typename _UniformRandomBitGenerator>
5812*38fd1498Szrj     _SampleIterator
5813*38fd1498Szrj     sample(_PopulationIterator __first, _PopulationIterator __last,
5814*38fd1498Szrj 	   _SampleIterator __out, _Distance __n,
5815*38fd1498Szrj 	   _UniformRandomBitGenerator&& __g)
5816*38fd1498Szrj     {
5817*38fd1498Szrj       using __pop_cat = typename
5818*38fd1498Szrj 	std::iterator_traits<_PopulationIterator>::iterator_category;
5819*38fd1498Szrj       using __samp_cat = typename
5820*38fd1498Szrj 	std::iterator_traits<_SampleIterator>::iterator_category;
5821*38fd1498Szrj 
5822*38fd1498Szrj       static_assert(
5823*38fd1498Szrj 	  __or_<is_convertible<__pop_cat, forward_iterator_tag>,
5824*38fd1498Szrj 		is_convertible<__samp_cat, random_access_iterator_tag>>::value,
5825*38fd1498Szrj 	  "output range must use a RandomAccessIterator when input range"
5826*38fd1498Szrj 	  " does not meet the ForwardIterator requirements");
5827*38fd1498Szrj 
5828*38fd1498Szrj       static_assert(is_integral<_Distance>::value,
5829*38fd1498Szrj 		    "sample size must be an integer type");
5830*38fd1498Szrj 
5831*38fd1498Szrj       typename iterator_traits<_PopulationIterator>::difference_type __d = __n;
5832*38fd1498Szrj       return _GLIBCXX_STD_A::
5833*38fd1498Szrj 	__sample(__first, __last, __pop_cat{}, __out, __samp_cat{}, __d,
5834*38fd1498Szrj 		 std::forward<_UniformRandomBitGenerator>(__g));
5835*38fd1498Szrj     }
5836*38fd1498Szrj #endif // C++17
5837*38fd1498Szrj #endif // C++14
5838*38fd1498Szrj 
5839*38fd1498Szrj _GLIBCXX_END_NAMESPACE_ALGO
5840*38fd1498Szrj _GLIBCXX_END_NAMESPACE_VERSION
5841*38fd1498Szrj } // namespace std
5842*38fd1498Szrj 
5843*38fd1498Szrj #endif /* _STL_ALGO_H */
5844