10b57cec5SDimitry Andric// -*- C++ -*- 20b57cec5SDimitry Andric//===-------------------------- algorithm ---------------------------------===// 30b57cec5SDimitry Andric// 40b57cec5SDimitry Andric// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 50b57cec5SDimitry Andric// See https://llvm.org/LICENSE.txt for license information. 60b57cec5SDimitry Andric// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 70b57cec5SDimitry Andric// 80b57cec5SDimitry Andric//===----------------------------------------------------------------------===// 90b57cec5SDimitry Andric 100b57cec5SDimitry Andric#ifndef _LIBCPP_ALGORITHM 110b57cec5SDimitry Andric#define _LIBCPP_ALGORITHM 120b57cec5SDimitry Andric 130b57cec5SDimitry Andric/* 140b57cec5SDimitry Andric algorithm synopsis 150b57cec5SDimitry Andric 160b57cec5SDimitry Andric#include <initializer_list> 170b57cec5SDimitry Andric 180b57cec5SDimitry Andricnamespace std 190b57cec5SDimitry Andric{ 200b57cec5SDimitry Andric 210b57cec5SDimitry Andrictemplate <class InputIterator, class Predicate> 220b57cec5SDimitry Andric constexpr bool // constexpr in C++20 230b57cec5SDimitry Andric all_of(InputIterator first, InputIterator last, Predicate pred); 240b57cec5SDimitry Andric 250b57cec5SDimitry Andrictemplate <class InputIterator, class Predicate> 260b57cec5SDimitry Andric constexpr bool // constexpr in C++20 270b57cec5SDimitry Andric any_of(InputIterator first, InputIterator last, Predicate pred); 280b57cec5SDimitry Andric 290b57cec5SDimitry Andrictemplate <class InputIterator, class Predicate> 300b57cec5SDimitry Andric constexpr bool // constexpr in C++20 310b57cec5SDimitry Andric none_of(InputIterator first, InputIterator last, Predicate pred); 320b57cec5SDimitry Andric 330b57cec5SDimitry Andrictemplate <class InputIterator, class Function> 340b57cec5SDimitry Andric constexpr Function // constexpr in C++20 350b57cec5SDimitry Andric for_each(InputIterator first, InputIterator last, Function f); 360b57cec5SDimitry Andric 370b57cec5SDimitry Andrictemplate<class InputIterator, class Size, class Function> 380b57cec5SDimitry Andric constexpr InputIterator // constexpr in C++20 390b57cec5SDimitry Andric for_each_n(InputIterator first, Size n, Function f); // C++17 400b57cec5SDimitry Andric 410b57cec5SDimitry Andrictemplate <class InputIterator, class T> 420b57cec5SDimitry Andric constexpr InputIterator // constexpr in C++20 430b57cec5SDimitry Andric find(InputIterator first, InputIterator last, const T& value); 440b57cec5SDimitry Andric 450b57cec5SDimitry Andrictemplate <class InputIterator, class Predicate> 460b57cec5SDimitry Andric constexpr InputIterator // constexpr in C++20 470b57cec5SDimitry Andric find_if(InputIterator first, InputIterator last, Predicate pred); 480b57cec5SDimitry Andric 490b57cec5SDimitry Andrictemplate<class InputIterator, class Predicate> 50*e8d8bef9SDimitry Andric constexpr InputIterator // constexpr in C++20 510b57cec5SDimitry Andric find_if_not(InputIterator first, InputIterator last, Predicate pred); 520b57cec5SDimitry Andric 530b57cec5SDimitry Andrictemplate <class ForwardIterator1, class ForwardIterator2> 54*e8d8bef9SDimitry Andric constexpr ForwardIterator1 // constexpr in C++20 550b57cec5SDimitry Andric find_end(ForwardIterator1 first1, ForwardIterator1 last1, 560b57cec5SDimitry Andric ForwardIterator2 first2, ForwardIterator2 last2); 570b57cec5SDimitry Andric 580b57cec5SDimitry Andrictemplate <class ForwardIterator1, class ForwardIterator2, class BinaryPredicate> 59*e8d8bef9SDimitry Andric constexpr ForwardIterator1 // constexpr in C++20 600b57cec5SDimitry Andric find_end(ForwardIterator1 first1, ForwardIterator1 last1, 610b57cec5SDimitry Andric ForwardIterator2 first2, ForwardIterator2 last2, BinaryPredicate pred); 620b57cec5SDimitry Andric 630b57cec5SDimitry Andrictemplate <class ForwardIterator1, class ForwardIterator2> 640b57cec5SDimitry Andric constexpr ForwardIterator1 // constexpr in C++20 650b57cec5SDimitry Andric find_first_of(ForwardIterator1 first1, ForwardIterator1 last1, 660b57cec5SDimitry Andric ForwardIterator2 first2, ForwardIterator2 last2); 670b57cec5SDimitry Andric 680b57cec5SDimitry Andrictemplate <class ForwardIterator1, class ForwardIterator2, class BinaryPredicate> 690b57cec5SDimitry Andric constexpr ForwardIterator1 // constexpr in C++20 700b57cec5SDimitry Andric find_first_of(ForwardIterator1 first1, ForwardIterator1 last1, 710b57cec5SDimitry Andric ForwardIterator2 first2, ForwardIterator2 last2, BinaryPredicate pred); 720b57cec5SDimitry Andric 730b57cec5SDimitry Andrictemplate <class ForwardIterator> 740b57cec5SDimitry Andric constexpr ForwardIterator // constexpr in C++20 750b57cec5SDimitry Andric adjacent_find(ForwardIterator first, ForwardIterator last); 760b57cec5SDimitry Andric 770b57cec5SDimitry Andrictemplate <class ForwardIterator, class BinaryPredicate> 780b57cec5SDimitry Andric constexpr ForwardIterator // constexpr in C++20 790b57cec5SDimitry Andric adjacent_find(ForwardIterator first, ForwardIterator last, BinaryPredicate pred); 800b57cec5SDimitry Andric 810b57cec5SDimitry Andrictemplate <class InputIterator, class T> 820b57cec5SDimitry Andric constexpr typename iterator_traits<InputIterator>::difference_type // constexpr in C++20 830b57cec5SDimitry Andric count(InputIterator first, InputIterator last, const T& value); 840b57cec5SDimitry Andric 850b57cec5SDimitry Andrictemplate <class InputIterator, class Predicate> 860b57cec5SDimitry Andric constexpr typename iterator_traits<InputIterator>::difference_type // constexpr in C++20 870b57cec5SDimitry Andric count_if(InputIterator first, InputIterator last, Predicate pred); 880b57cec5SDimitry Andric 890b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2> 900b57cec5SDimitry Andric constexpr pair<InputIterator1, InputIterator2> // constexpr in C++20 910b57cec5SDimitry Andric mismatch(InputIterator1 first1, InputIterator1 last1, InputIterator2 first2); 920b57cec5SDimitry Andric 930b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2> 940b57cec5SDimitry Andric constexpr pair<InputIterator1, InputIterator2> // constexpr in C++20 950b57cec5SDimitry Andric mismatch(InputIterator1 first1, InputIterator1 last1, 960b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2); // **C++14** 970b57cec5SDimitry Andric 980b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class BinaryPredicate> 990b57cec5SDimitry Andric constexpr pair<InputIterator1, InputIterator2> // constexpr in C++20 1000b57cec5SDimitry Andric mismatch(InputIterator1 first1, InputIterator1 last1, 1010b57cec5SDimitry Andric InputIterator2 first2, BinaryPredicate pred); 1020b57cec5SDimitry Andric 1030b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class BinaryPredicate> 1040b57cec5SDimitry Andric constexpr pair<InputIterator1, InputIterator2> // constexpr in C++20 1050b57cec5SDimitry Andric mismatch(InputIterator1 first1, InputIterator1 last1, 1060b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2, 1070b57cec5SDimitry Andric BinaryPredicate pred); // **C++14** 1080b57cec5SDimitry Andric 1090b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2> 1100b57cec5SDimitry Andric constexpr bool // constexpr in C++20 1110b57cec5SDimitry Andric equal(InputIterator1 first1, InputIterator1 last1, InputIterator2 first2); 1120b57cec5SDimitry Andric 1130b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2> 1140b57cec5SDimitry Andric constexpr bool // constexpr in C++20 1150b57cec5SDimitry Andric equal(InputIterator1 first1, InputIterator1 last1, 1160b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2); // **C++14** 1170b57cec5SDimitry Andric 1180b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class BinaryPredicate> 1190b57cec5SDimitry Andric constexpr bool // constexpr in C++20 1200b57cec5SDimitry Andric equal(InputIterator1 first1, InputIterator1 last1, 1210b57cec5SDimitry Andric InputIterator2 first2, BinaryPredicate pred); 1220b57cec5SDimitry Andric 1230b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class BinaryPredicate> 1240b57cec5SDimitry Andric constexpr bool // constexpr in C++20 1250b57cec5SDimitry Andric equal(InputIterator1 first1, InputIterator1 last1, 1260b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2, 1270b57cec5SDimitry Andric BinaryPredicate pred); // **C++14** 1280b57cec5SDimitry Andric 1290b57cec5SDimitry Andrictemplate<class ForwardIterator1, class ForwardIterator2> 1300b57cec5SDimitry Andric constexpr bool // constexpr in C++20 1310b57cec5SDimitry Andric is_permutation(ForwardIterator1 first1, ForwardIterator1 last1, 1320b57cec5SDimitry Andric ForwardIterator2 first2); 1330b57cec5SDimitry Andric 1340b57cec5SDimitry Andrictemplate<class ForwardIterator1, class ForwardIterator2> 1350b57cec5SDimitry Andric constexpr bool // constexpr in C++20 1360b57cec5SDimitry Andric is_permutation(ForwardIterator1 first1, ForwardIterator1 last1, 1370b57cec5SDimitry Andric ForwardIterator2 first2, ForwardIterator2 last2); // **C++14** 1380b57cec5SDimitry Andric 1390b57cec5SDimitry Andrictemplate<class ForwardIterator1, class ForwardIterator2, class BinaryPredicate> 1400b57cec5SDimitry Andric constexpr bool // constexpr in C++20 1410b57cec5SDimitry Andric is_permutation(ForwardIterator1 first1, ForwardIterator1 last1, 1420b57cec5SDimitry Andric ForwardIterator2 first2, BinaryPredicate pred); 1430b57cec5SDimitry Andric 1440b57cec5SDimitry Andrictemplate<class ForwardIterator1, class ForwardIterator2, class BinaryPredicate> 1450b57cec5SDimitry Andric constexpr bool // constexpr in C++20 1460b57cec5SDimitry Andric is_permutation(ForwardIterator1 first1, ForwardIterator1 last1, 1470b57cec5SDimitry Andric ForwardIterator2 first2, ForwardIterator2 last2, 1480b57cec5SDimitry Andric BinaryPredicate pred); // **C++14** 1490b57cec5SDimitry Andric 1500b57cec5SDimitry Andrictemplate <class ForwardIterator1, class ForwardIterator2> 1510b57cec5SDimitry Andric constexpr ForwardIterator1 // constexpr in C++20 1520b57cec5SDimitry Andric search(ForwardIterator1 first1, ForwardIterator1 last1, 1530b57cec5SDimitry Andric ForwardIterator2 first2, ForwardIterator2 last2); 1540b57cec5SDimitry Andric 1550b57cec5SDimitry Andrictemplate <class ForwardIterator1, class ForwardIterator2, class BinaryPredicate> 1560b57cec5SDimitry Andric constexpr ForwardIterator1 // constexpr in C++20 1570b57cec5SDimitry Andric search(ForwardIterator1 first1, ForwardIterator1 last1, 1580b57cec5SDimitry Andric ForwardIterator2 first2, ForwardIterator2 last2, BinaryPredicate pred); 1590b57cec5SDimitry Andric 1600b57cec5SDimitry Andrictemplate <class ForwardIterator, class Size, class T> 1610b57cec5SDimitry Andric constexpr ForwardIterator // constexpr in C++20 1620b57cec5SDimitry Andric search_n(ForwardIterator first, ForwardIterator last, Size count, const T& value); 1630b57cec5SDimitry Andric 1640b57cec5SDimitry Andrictemplate <class ForwardIterator, class Size, class T, class BinaryPredicate> 1650b57cec5SDimitry Andric constexpr ForwardIterator // constexpr in C++20 1660b57cec5SDimitry Andric search_n(ForwardIterator first, ForwardIterator last, 1670b57cec5SDimitry Andric Size count, const T& value, BinaryPredicate pred); 1680b57cec5SDimitry Andric 1690b57cec5SDimitry Andrictemplate <class InputIterator, class OutputIterator> 170480093f4SDimitry Andric constexpr OutputIterator // constexpr in C++20 1710b57cec5SDimitry Andric copy(InputIterator first, InputIterator last, OutputIterator result); 1720b57cec5SDimitry Andric 1730b57cec5SDimitry Andrictemplate<class InputIterator, class OutputIterator, class Predicate> 174480093f4SDimitry Andric constexpr OutputIterator // constexpr in C++20 1750b57cec5SDimitry Andric copy_if(InputIterator first, InputIterator last, 1760b57cec5SDimitry Andric OutputIterator result, Predicate pred); 1770b57cec5SDimitry Andric 1780b57cec5SDimitry Andrictemplate<class InputIterator, class Size, class OutputIterator> 179480093f4SDimitry Andric constexpr OutputIterator // constexpr in C++20 1800b57cec5SDimitry Andric copy_n(InputIterator first, Size n, OutputIterator result); 1810b57cec5SDimitry Andric 1820b57cec5SDimitry Andrictemplate <class BidirectionalIterator1, class BidirectionalIterator2> 183480093f4SDimitry Andric constexpr BidirectionalIterator2 // constexpr in C++20 1840b57cec5SDimitry Andric copy_backward(BidirectionalIterator1 first, BidirectionalIterator1 last, 1850b57cec5SDimitry Andric BidirectionalIterator2 result); 1860b57cec5SDimitry Andric 1870b57cec5SDimitry Andrictemplate <class ForwardIterator1, class ForwardIterator2> 188*e8d8bef9SDimitry Andric constexpr ForwardIterator2 // constexpr in C++20 1890b57cec5SDimitry Andric swap_ranges(ForwardIterator1 first1, ForwardIterator1 last1, ForwardIterator2 first2); 1900b57cec5SDimitry Andric 1910b57cec5SDimitry Andrictemplate <class ForwardIterator1, class ForwardIterator2> 192*e8d8bef9SDimitry Andric constexpr void // constexpr in C++20 1930b57cec5SDimitry Andric iter_swap(ForwardIterator1 a, ForwardIterator2 b); 1940b57cec5SDimitry Andric 1950b57cec5SDimitry Andrictemplate <class InputIterator, class OutputIterator, class UnaryOperation> 1960b57cec5SDimitry Andric constexpr OutputIterator // constexpr in C++20 1970b57cec5SDimitry Andric transform(InputIterator first, InputIterator last, OutputIterator result, UnaryOperation op); 1980b57cec5SDimitry Andric 1990b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class OutputIterator, class BinaryOperation> 2000b57cec5SDimitry Andric constexpr OutputIterator // constexpr in C++20 2010b57cec5SDimitry Andric transform(InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, 2020b57cec5SDimitry Andric OutputIterator result, BinaryOperation binary_op); 2030b57cec5SDimitry Andric 2040b57cec5SDimitry Andrictemplate <class ForwardIterator, class T> 2050b57cec5SDimitry Andric constexpr void // constexpr in C++20 2060b57cec5SDimitry Andric replace(ForwardIterator first, ForwardIterator last, const T& old_value, const T& new_value); 2070b57cec5SDimitry Andric 2080b57cec5SDimitry Andrictemplate <class ForwardIterator, class Predicate, class T> 2090b57cec5SDimitry Andric constexpr void // constexpr in C++20 2100b57cec5SDimitry Andric replace_if(ForwardIterator first, ForwardIterator last, Predicate pred, const T& new_value); 2110b57cec5SDimitry Andric 2120b57cec5SDimitry Andrictemplate <class InputIterator, class OutputIterator, class T> 2130b57cec5SDimitry Andric constexpr OutputIterator // constexpr in C++20 2140b57cec5SDimitry Andric replace_copy(InputIterator first, InputIterator last, OutputIterator result, 2150b57cec5SDimitry Andric const T& old_value, const T& new_value); 2160b57cec5SDimitry Andric 2170b57cec5SDimitry Andrictemplate <class InputIterator, class OutputIterator, class Predicate, class T> 2180b57cec5SDimitry Andric constexpr OutputIterator // constexpr in C++20 2190b57cec5SDimitry Andric replace_copy_if(InputIterator first, InputIterator last, OutputIterator result, Predicate pred, const T& new_value); 2200b57cec5SDimitry Andric 2210b57cec5SDimitry Andrictemplate <class ForwardIterator, class T> 2220b57cec5SDimitry Andric constexpr void // constexpr in C++20 2230b57cec5SDimitry Andric fill(ForwardIterator first, ForwardIterator last, const T& value); 2240b57cec5SDimitry Andric 2250b57cec5SDimitry Andrictemplate <class OutputIterator, class Size, class T> 2260b57cec5SDimitry Andric constexpr OutputIterator // constexpr in C++20 2270b57cec5SDimitry Andric fill_n(OutputIterator first, Size n, const T& value); 2280b57cec5SDimitry Andric 2290b57cec5SDimitry Andrictemplate <class ForwardIterator, class Generator> 2300b57cec5SDimitry Andric constexpr void // constexpr in C++20 2310b57cec5SDimitry Andric generate(ForwardIterator first, ForwardIterator last, Generator gen); 2320b57cec5SDimitry Andric 2330b57cec5SDimitry Andrictemplate <class OutputIterator, class Size, class Generator> 2340b57cec5SDimitry Andric constexpr OutputIterator // constexpr in C++20 2350b57cec5SDimitry Andric generate_n(OutputIterator first, Size n, Generator gen); 2360b57cec5SDimitry Andric 2370b57cec5SDimitry Andrictemplate <class ForwardIterator, class T> 2380b57cec5SDimitry Andric constexpr ForwardIterator // constexpr in C++20 2390b57cec5SDimitry Andric remove(ForwardIterator first, ForwardIterator last, const T& value); 2400b57cec5SDimitry Andric 2410b57cec5SDimitry Andrictemplate <class ForwardIterator, class Predicate> 2420b57cec5SDimitry Andric constexpr ForwardIterator // constexpr in C++20 2430b57cec5SDimitry Andric remove_if(ForwardIterator first, ForwardIterator last, Predicate pred); 2440b57cec5SDimitry Andric 2450b57cec5SDimitry Andrictemplate <class InputIterator, class OutputIterator, class T> 2460b57cec5SDimitry Andric constexpr OutputIterator // constexpr in C++20 2470b57cec5SDimitry Andric remove_copy(InputIterator first, InputIterator last, OutputIterator result, const T& value); 2480b57cec5SDimitry Andric 2490b57cec5SDimitry Andrictemplate <class InputIterator, class OutputIterator, class Predicate> 2500b57cec5SDimitry Andric constexpr OutputIterator // constexpr in C++20 2510b57cec5SDimitry Andric remove_copy_if(InputIterator first, InputIterator last, OutputIterator result, Predicate pred); 2520b57cec5SDimitry Andric 2530b57cec5SDimitry Andrictemplate <class ForwardIterator> 254*e8d8bef9SDimitry Andric constexpr ForwardIterator // constexpr in C++20 2550b57cec5SDimitry Andric unique(ForwardIterator first, ForwardIterator last); 2560b57cec5SDimitry Andric 2570b57cec5SDimitry Andrictemplate <class ForwardIterator, class BinaryPredicate> 258*e8d8bef9SDimitry Andric constexpr ForwardIterator // constexpr in C++20 2590b57cec5SDimitry Andric unique(ForwardIterator first, ForwardIterator last, BinaryPredicate pred); 2600b57cec5SDimitry Andric 2610b57cec5SDimitry Andrictemplate <class InputIterator, class OutputIterator> 262*e8d8bef9SDimitry Andric constexpr OutputIterator // constexpr in C++20 2630b57cec5SDimitry Andric unique_copy(InputIterator first, InputIterator last, OutputIterator result); 2640b57cec5SDimitry Andric 2650b57cec5SDimitry Andrictemplate <class InputIterator, class OutputIterator, class BinaryPredicate> 266*e8d8bef9SDimitry Andric constexpr OutputIterator // constexpr in C++20 2670b57cec5SDimitry Andric unique_copy(InputIterator first, InputIterator last, OutputIterator result, BinaryPredicate pred); 2680b57cec5SDimitry Andric 2690b57cec5SDimitry Andrictemplate <class BidirectionalIterator> 270*e8d8bef9SDimitry Andric constexpr void // constexpr in C++20 2710b57cec5SDimitry Andric reverse(BidirectionalIterator first, BidirectionalIterator last); 2720b57cec5SDimitry Andric 2730b57cec5SDimitry Andrictemplate <class BidirectionalIterator, class OutputIterator> 2740b57cec5SDimitry Andric constexpr OutputIterator // constexpr in C++20 2750b57cec5SDimitry Andric reverse_copy(BidirectionalIterator first, BidirectionalIterator last, OutputIterator result); 2760b57cec5SDimitry Andric 2770b57cec5SDimitry Andrictemplate <class ForwardIterator> 278*e8d8bef9SDimitry Andric constexpr ForwardIterator // constexpr in C++20 2790b57cec5SDimitry Andric rotate(ForwardIterator first, ForwardIterator middle, ForwardIterator last); 2800b57cec5SDimitry Andric 2810b57cec5SDimitry Andrictemplate <class ForwardIterator, class OutputIterator> 282*e8d8bef9SDimitry Andric constexpr OutputIterator // constexpr in C++20 2830b57cec5SDimitry Andric rotate_copy(ForwardIterator first, ForwardIterator middle, ForwardIterator last, OutputIterator result); 2840b57cec5SDimitry Andric 2850b57cec5SDimitry Andrictemplate <class RandomAccessIterator> 2860b57cec5SDimitry Andric void 2870b57cec5SDimitry Andric random_shuffle(RandomAccessIterator first, RandomAccessIterator last); // deprecated in C++14, removed in C++17 2880b57cec5SDimitry Andric 2890b57cec5SDimitry Andrictemplate <class RandomAccessIterator, class RandomNumberGenerator> 2900b57cec5SDimitry Andric void 2910b57cec5SDimitry Andric random_shuffle(RandomAccessIterator first, RandomAccessIterator last, 2920b57cec5SDimitry Andric RandomNumberGenerator& rand); // deprecated in C++14, removed in C++17 2930b57cec5SDimitry Andric 2940b57cec5SDimitry Andrictemplate<class PopulationIterator, class SampleIterator, 2950b57cec5SDimitry Andric class Distance, class UniformRandomBitGenerator> 2960b57cec5SDimitry Andric SampleIterator sample(PopulationIterator first, PopulationIterator last, 2970b57cec5SDimitry Andric SampleIterator out, Distance n, 2980b57cec5SDimitry Andric UniformRandomBitGenerator&& g); // C++17 2990b57cec5SDimitry Andric 3000b57cec5SDimitry Andrictemplate<class RandomAccessIterator, class UniformRandomNumberGenerator> 3010b57cec5SDimitry Andric void shuffle(RandomAccessIterator first, RandomAccessIterator last, 3020b57cec5SDimitry Andric UniformRandomNumberGenerator&& g); 3030b57cec5SDimitry Andric 304*e8d8bef9SDimitry Andrictemplate<class ForwardIterator> 305*e8d8bef9SDimitry Andric constexpr ForwardIterator 306*e8d8bef9SDimitry Andric shift_left(ForwardIterator first, ForwardIterator last, 307*e8d8bef9SDimitry Andric typename iterator_traits<ForwardIterator>::difference_type n); // C++20 308*e8d8bef9SDimitry Andric 309*e8d8bef9SDimitry Andrictemplate<class ForwardIterator> 310*e8d8bef9SDimitry Andric constexpr ForwardIterator 311*e8d8bef9SDimitry Andric shift_right(ForwardIterator first, ForwardIterator last, 312*e8d8bef9SDimitry Andric typename iterator_traits<ForwardIterator>::difference_type n); // C++20 313*e8d8bef9SDimitry Andric 3140b57cec5SDimitry Andrictemplate <class InputIterator, class Predicate> 3150b57cec5SDimitry Andric constexpr bool // constexpr in C++20 3160b57cec5SDimitry Andric is_partitioned(InputIterator first, InputIterator last, Predicate pred); 3170b57cec5SDimitry Andric 3180b57cec5SDimitry Andrictemplate <class ForwardIterator, class Predicate> 319*e8d8bef9SDimitry Andric constexpr ForwardIterator // constexpr in C++20 3200b57cec5SDimitry Andric partition(ForwardIterator first, ForwardIterator last, Predicate pred); 3210b57cec5SDimitry Andric 3220b57cec5SDimitry Andrictemplate <class InputIterator, class OutputIterator1, 3230b57cec5SDimitry Andric class OutputIterator2, class Predicate> 3240b57cec5SDimitry Andric constexpr pair<OutputIterator1, OutputIterator2> // constexpr in C++20 3250b57cec5SDimitry Andric partition_copy(InputIterator first, InputIterator last, 3260b57cec5SDimitry Andric OutputIterator1 out_true, OutputIterator2 out_false, 3270b57cec5SDimitry Andric Predicate pred); 3280b57cec5SDimitry Andric 3290b57cec5SDimitry Andrictemplate <class ForwardIterator, class Predicate> 3300b57cec5SDimitry Andric ForwardIterator 3310b57cec5SDimitry Andric stable_partition(ForwardIterator first, ForwardIterator last, Predicate pred); 3320b57cec5SDimitry Andric 3330b57cec5SDimitry Andrictemplate<class ForwardIterator, class Predicate> 3340b57cec5SDimitry Andric constexpr ForwardIterator // constexpr in C++20 3350b57cec5SDimitry Andric partition_point(ForwardIterator first, ForwardIterator last, Predicate pred); 3360b57cec5SDimitry Andric 3370b57cec5SDimitry Andrictemplate <class ForwardIterator> 3380b57cec5SDimitry Andric constexpr bool // constexpr in C++20 3390b57cec5SDimitry Andric is_sorted(ForwardIterator first, ForwardIterator last); 3400b57cec5SDimitry Andric 3410b57cec5SDimitry Andrictemplate <class ForwardIterator, class Compare> 342*e8d8bef9SDimitry Andric constexpr bool // constexpr in C++20 3430b57cec5SDimitry Andric is_sorted(ForwardIterator first, ForwardIterator last, Compare comp); 3440b57cec5SDimitry Andric 3450b57cec5SDimitry Andrictemplate<class ForwardIterator> 3460b57cec5SDimitry Andric constexpr ForwardIterator // constexpr in C++20 3470b57cec5SDimitry Andric is_sorted_until(ForwardIterator first, ForwardIterator last); 3480b57cec5SDimitry Andric 3490b57cec5SDimitry Andrictemplate <class ForwardIterator, class Compare> 3500b57cec5SDimitry Andric constexpr ForwardIterator // constexpr in C++20 3510b57cec5SDimitry Andric is_sorted_until(ForwardIterator first, ForwardIterator last, Compare comp); 3520b57cec5SDimitry Andric 3530b57cec5SDimitry Andrictemplate <class RandomAccessIterator> 3540b57cec5SDimitry Andric void 3550b57cec5SDimitry Andric sort(RandomAccessIterator first, RandomAccessIterator last); 3560b57cec5SDimitry Andric 3570b57cec5SDimitry Andrictemplate <class RandomAccessIterator, class Compare> 3580b57cec5SDimitry Andric void 3590b57cec5SDimitry Andric sort(RandomAccessIterator first, RandomAccessIterator last, Compare comp); 3600b57cec5SDimitry Andric 3610b57cec5SDimitry Andrictemplate <class RandomAccessIterator> 3620b57cec5SDimitry Andric void 3630b57cec5SDimitry Andric stable_sort(RandomAccessIterator first, RandomAccessIterator last); 3640b57cec5SDimitry Andric 3650b57cec5SDimitry Andrictemplate <class RandomAccessIterator, class Compare> 3660b57cec5SDimitry Andric void 3670b57cec5SDimitry Andric stable_sort(RandomAccessIterator first, RandomAccessIterator last, Compare comp); 3680b57cec5SDimitry Andric 3690b57cec5SDimitry Andrictemplate <class RandomAccessIterator> 3700b57cec5SDimitry Andric void 3710b57cec5SDimitry Andric partial_sort(RandomAccessIterator first, RandomAccessIterator middle, RandomAccessIterator last); 3720b57cec5SDimitry Andric 3730b57cec5SDimitry Andrictemplate <class RandomAccessIterator, class Compare> 3740b57cec5SDimitry Andric void 3750b57cec5SDimitry Andric partial_sort(RandomAccessIterator first, RandomAccessIterator middle, RandomAccessIterator last, Compare comp); 3760b57cec5SDimitry Andric 3770b57cec5SDimitry Andrictemplate <class InputIterator, class RandomAccessIterator> 3780b57cec5SDimitry Andric RandomAccessIterator 3790b57cec5SDimitry Andric partial_sort_copy(InputIterator first, InputIterator last, 3800b57cec5SDimitry Andric RandomAccessIterator result_first, RandomAccessIterator result_last); 3810b57cec5SDimitry Andric 3820b57cec5SDimitry Andrictemplate <class InputIterator, class RandomAccessIterator, class Compare> 3830b57cec5SDimitry Andric RandomAccessIterator 3840b57cec5SDimitry Andric partial_sort_copy(InputIterator first, InputIterator last, 3850b57cec5SDimitry Andric RandomAccessIterator result_first, RandomAccessIterator result_last, Compare comp); 3860b57cec5SDimitry Andric 3870b57cec5SDimitry Andrictemplate <class RandomAccessIterator> 3880b57cec5SDimitry Andric void 3890b57cec5SDimitry Andric nth_element(RandomAccessIterator first, RandomAccessIterator nth, RandomAccessIterator last); 3900b57cec5SDimitry Andric 3910b57cec5SDimitry Andrictemplate <class RandomAccessIterator, class Compare> 3920b57cec5SDimitry Andric void 3930b57cec5SDimitry Andric nth_element(RandomAccessIterator first, RandomAccessIterator nth, RandomAccessIterator last, Compare comp); 3940b57cec5SDimitry Andric 3950b57cec5SDimitry Andrictemplate <class ForwardIterator, class T> 3960b57cec5SDimitry Andric constexpr ForwardIterator // constexpr in C++20 3970b57cec5SDimitry Andric lower_bound(ForwardIterator first, ForwardIterator last, const T& value); 3980b57cec5SDimitry Andric 3990b57cec5SDimitry Andrictemplate <class ForwardIterator, class T, class Compare> 4000b57cec5SDimitry Andric constexpr ForwardIterator // constexpr in C++20 4010b57cec5SDimitry Andric lower_bound(ForwardIterator first, ForwardIterator last, const T& value, Compare comp); 4020b57cec5SDimitry Andric 4030b57cec5SDimitry Andrictemplate <class ForwardIterator, class T> 4040b57cec5SDimitry Andric constexpr ForwardIterator // constexpr in C++20 4050b57cec5SDimitry Andric upper_bound(ForwardIterator first, ForwardIterator last, const T& value); 4060b57cec5SDimitry Andric 4070b57cec5SDimitry Andrictemplate <class ForwardIterator, class T, class Compare> 4080b57cec5SDimitry Andric constexpr ForwardIterator // constexpr in C++20 4090b57cec5SDimitry Andric upper_bound(ForwardIterator first, ForwardIterator last, const T& value, Compare comp); 4100b57cec5SDimitry Andric 4110b57cec5SDimitry Andrictemplate <class ForwardIterator, class T> 4120b57cec5SDimitry Andric constexpr pair<ForwardIterator, ForwardIterator> // constexpr in C++20 4130b57cec5SDimitry Andric equal_range(ForwardIterator first, ForwardIterator last, const T& value); 4140b57cec5SDimitry Andric 4150b57cec5SDimitry Andrictemplate <class ForwardIterator, class T, class Compare> 4160b57cec5SDimitry Andric constexpr pair<ForwardIterator, ForwardIterator> // constexpr in C++20 4170b57cec5SDimitry Andric equal_range(ForwardIterator first, ForwardIterator last, const T& value, Compare comp); 4180b57cec5SDimitry Andric 4190b57cec5SDimitry Andrictemplate <class ForwardIterator, class T> 4200b57cec5SDimitry Andric constexpr bool // constexpr in C++20 4210b57cec5SDimitry Andric binary_search(ForwardIterator first, ForwardIterator last, const T& value); 4220b57cec5SDimitry Andric 4230b57cec5SDimitry Andrictemplate <class ForwardIterator, class T, class Compare> 4240b57cec5SDimitry Andric constexpr bool // constexpr in C++20 4250b57cec5SDimitry Andric binary_search(ForwardIterator first, ForwardIterator last, const T& value, Compare comp); 4260b57cec5SDimitry Andric 4270b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class OutputIterator> 428*e8d8bef9SDimitry Andric constexpr OutputIterator // constexpr in C++20 4290b57cec5SDimitry Andric merge(InputIterator1 first1, InputIterator1 last1, 4300b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2, OutputIterator result); 4310b57cec5SDimitry Andric 4320b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class OutputIterator, class Compare> 433*e8d8bef9SDimitry Andric constexpr OutputIterator // constexpr in C++20 4340b57cec5SDimitry Andric merge(InputIterator1 first1, InputIterator1 last1, 4350b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2, OutputIterator result, Compare comp); 4360b57cec5SDimitry Andric 4370b57cec5SDimitry Andrictemplate <class BidirectionalIterator> 4380b57cec5SDimitry Andric void 4390b57cec5SDimitry Andric inplace_merge(BidirectionalIterator first, BidirectionalIterator middle, BidirectionalIterator last); 4400b57cec5SDimitry Andric 4410b57cec5SDimitry Andrictemplate <class BidirectionalIterator, class Compare> 4420b57cec5SDimitry Andric void 4430b57cec5SDimitry Andric inplace_merge(BidirectionalIterator first, BidirectionalIterator middle, BidirectionalIterator last, Compare comp); 4440b57cec5SDimitry Andric 4450b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2> 4460b57cec5SDimitry Andric constexpr bool // constexpr in C++20 4470b57cec5SDimitry Andric includes(InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, InputIterator2 last2); 4480b57cec5SDimitry Andric 4490b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class Compare> 4500b57cec5SDimitry Andric constexpr bool // constexpr in C++20 4510b57cec5SDimitry Andric includes(InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, InputIterator2 last2, Compare comp); 4520b57cec5SDimitry Andric 4530b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class OutputIterator> 454*e8d8bef9SDimitry Andric constexpr OutputIterator // constexpr in C++20 4550b57cec5SDimitry Andric set_union(InputIterator1 first1, InputIterator1 last1, 4560b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2, OutputIterator result); 4570b57cec5SDimitry Andric 4580b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class OutputIterator, class Compare> 459*e8d8bef9SDimitry Andric constexpr OutputIterator // constexpr in C++20 4600b57cec5SDimitry Andric set_union(InputIterator1 first1, InputIterator1 last1, 4610b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2, OutputIterator result, Compare comp); 4620b57cec5SDimitry Andric 4630b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class OutputIterator> 4640b57cec5SDimitry Andric constexpr OutputIterator // constexpr in C++20 4650b57cec5SDimitry Andric set_intersection(InputIterator1 first1, InputIterator1 last1, 4660b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2, OutputIterator result); 4670b57cec5SDimitry Andric 4680b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class OutputIterator, class Compare> 4690b57cec5SDimitry Andric constexpr OutputIterator // constexpr in C++20 4700b57cec5SDimitry Andric set_intersection(InputIterator1 first1, InputIterator1 last1, 4710b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2, OutputIterator result, Compare comp); 4720b57cec5SDimitry Andric 4730b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class OutputIterator> 474*e8d8bef9SDimitry Andric constexpr OutputIterator // constexpr in C++20 4750b57cec5SDimitry Andric set_difference(InputIterator1 first1, InputIterator1 last1, 4760b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2, OutputIterator result); 4770b57cec5SDimitry Andric 4780b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class OutputIterator, class Compare> 479*e8d8bef9SDimitry Andric constexpr OutputIterator // constexpr in C++20 4800b57cec5SDimitry Andric set_difference(InputIterator1 first1, InputIterator1 last1, 4810b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2, OutputIterator result, Compare comp); 4820b57cec5SDimitry Andric 4830b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class OutputIterator> 484*e8d8bef9SDimitry Andric constexpr OutputIterator // constexpr in C++20 4850b57cec5SDimitry Andric set_symmetric_difference(InputIterator1 first1, InputIterator1 last1, 4860b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2, OutputIterator result); 4870b57cec5SDimitry Andric 4880b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class OutputIterator, class Compare> 489*e8d8bef9SDimitry Andric constexpr OutputIterator // constexpr in C++20 4900b57cec5SDimitry Andric set_symmetric_difference(InputIterator1 first1, InputIterator1 last1, 4910b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2, OutputIterator result, Compare comp); 4920b57cec5SDimitry Andric 4930b57cec5SDimitry Andrictemplate <class RandomAccessIterator> 4940b57cec5SDimitry Andric void 4950b57cec5SDimitry Andric push_heap(RandomAccessIterator first, RandomAccessIterator last); 4960b57cec5SDimitry Andric 4970b57cec5SDimitry Andrictemplate <class RandomAccessIterator, class Compare> 4980b57cec5SDimitry Andric void 4990b57cec5SDimitry Andric push_heap(RandomAccessIterator first, RandomAccessIterator last, Compare comp); 5000b57cec5SDimitry Andric 5010b57cec5SDimitry Andrictemplate <class RandomAccessIterator> 5020b57cec5SDimitry Andric void 5030b57cec5SDimitry Andric pop_heap(RandomAccessIterator first, RandomAccessIterator last); 5040b57cec5SDimitry Andric 5050b57cec5SDimitry Andrictemplate <class RandomAccessIterator, class Compare> 5060b57cec5SDimitry Andric void 5070b57cec5SDimitry Andric pop_heap(RandomAccessIterator first, RandomAccessIterator last, Compare comp); 5080b57cec5SDimitry Andric 5090b57cec5SDimitry Andrictemplate <class RandomAccessIterator> 5100b57cec5SDimitry Andric void 5110b57cec5SDimitry Andric make_heap(RandomAccessIterator first, RandomAccessIterator last); 5120b57cec5SDimitry Andric 5130b57cec5SDimitry Andrictemplate <class RandomAccessIterator, class Compare> 5140b57cec5SDimitry Andric void 5150b57cec5SDimitry Andric make_heap(RandomAccessIterator first, RandomAccessIterator last, Compare comp); 5160b57cec5SDimitry Andric 5170b57cec5SDimitry Andrictemplate <class RandomAccessIterator> 5180b57cec5SDimitry Andric void 5190b57cec5SDimitry Andric sort_heap(RandomAccessIterator first, RandomAccessIterator last); 5200b57cec5SDimitry Andric 5210b57cec5SDimitry Andrictemplate <class RandomAccessIterator, class Compare> 5220b57cec5SDimitry Andric void 5230b57cec5SDimitry Andric sort_heap(RandomAccessIterator first, RandomAccessIterator last, Compare comp); 5240b57cec5SDimitry Andric 5250b57cec5SDimitry Andrictemplate <class RandomAccessIterator> 5260b57cec5SDimitry Andric constexpr bool // constexpr in C++20 5270b57cec5SDimitry Andric is_heap(RandomAccessIterator first, RandomAccessiterator last); 5280b57cec5SDimitry Andric 5290b57cec5SDimitry Andrictemplate <class RandomAccessIterator, class Compare> 5300b57cec5SDimitry Andric constexpr bool // constexpr in C++20 5310b57cec5SDimitry Andric is_heap(RandomAccessIterator first, RandomAccessiterator last, Compare comp); 5320b57cec5SDimitry Andric 5330b57cec5SDimitry Andrictemplate <class RandomAccessIterator> 5340b57cec5SDimitry Andric constexpr RandomAccessIterator // constexpr in C++20 5350b57cec5SDimitry Andric is_heap_until(RandomAccessIterator first, RandomAccessiterator last); 5360b57cec5SDimitry Andric 5370b57cec5SDimitry Andrictemplate <class RandomAccessIterator, class Compare> 5380b57cec5SDimitry Andric constexpr RandomAccessIterator // constexpr in C++20 5390b57cec5SDimitry Andric is_heap_until(RandomAccessIterator first, RandomAccessiterator last, Compare comp); 5400b57cec5SDimitry Andric 5410b57cec5SDimitry Andrictemplate <class ForwardIterator> 542*e8d8bef9SDimitry Andric constexpr ForwardIterator // constexpr in C++14 543*e8d8bef9SDimitry Andric min_element(ForwardIterator first, ForwardIterator last); 5440b57cec5SDimitry Andric 5450b57cec5SDimitry Andrictemplate <class ForwardIterator, class Compare> 546*e8d8bef9SDimitry Andric constexpr ForwardIterator // constexpr in C++14 547*e8d8bef9SDimitry Andric min_element(ForwardIterator first, ForwardIterator last, Compare comp); 5480b57cec5SDimitry Andric 5490b57cec5SDimitry Andrictemplate <class T> 550*e8d8bef9SDimitry Andric constexpr const T& // constexpr in C++14 551*e8d8bef9SDimitry Andric min(const T& a, const T& b); 5520b57cec5SDimitry Andric 5530b57cec5SDimitry Andrictemplate <class T, class Compare> 554*e8d8bef9SDimitry Andric constexpr const T& // constexpr in C++14 555*e8d8bef9SDimitry Andric min(const T& a, const T& b, Compare comp); 5560b57cec5SDimitry Andric 5570b57cec5SDimitry Andrictemplate<class T> 558*e8d8bef9SDimitry Andric constexpr T // constexpr in C++14 559*e8d8bef9SDimitry Andric min(initializer_list<T> t); 5600b57cec5SDimitry Andric 5610b57cec5SDimitry Andrictemplate<class T, class Compare> 562*e8d8bef9SDimitry Andric constexpr T // constexpr in C++14 563*e8d8bef9SDimitry Andric min(initializer_list<T> t, Compare comp); 5640b57cec5SDimitry Andric 5650b57cec5SDimitry Andrictemplate<class T> 5660b57cec5SDimitry Andric constexpr const T& clamp(const T& v, const T& lo, const T& hi); // C++17 5670b57cec5SDimitry Andric 5680b57cec5SDimitry Andrictemplate<class T, class Compare> 5690b57cec5SDimitry Andric constexpr const T& clamp(const T& v, const T& lo, const T& hi, Compare comp); // C++17 5700b57cec5SDimitry Andric 5710b57cec5SDimitry Andrictemplate <class ForwardIterator> 572*e8d8bef9SDimitry Andric constexpr ForwardIterator // constexpr in C++14 573*e8d8bef9SDimitry Andric max_element(ForwardIterator first, ForwardIterator last); 5740b57cec5SDimitry Andric 5750b57cec5SDimitry Andrictemplate <class ForwardIterator, class Compare> 576*e8d8bef9SDimitry Andric constexpr ForwardIterator // constexpr in C++14 577*e8d8bef9SDimitry Andric max_element(ForwardIterator first, ForwardIterator last, Compare comp); 5780b57cec5SDimitry Andric 5790b57cec5SDimitry Andrictemplate <class T> 580*e8d8bef9SDimitry Andric constexpr const T& // constexpr in C++14 581*e8d8bef9SDimitry Andric max(const T& a, const T& b); 5820b57cec5SDimitry Andric 5830b57cec5SDimitry Andrictemplate <class T, class Compare> 584*e8d8bef9SDimitry Andric constexpr const T& // constexpr in C++14 585*e8d8bef9SDimitry Andric max(const T& a, const T& b, Compare comp); 5860b57cec5SDimitry Andric 5870b57cec5SDimitry Andrictemplate<class T> 588*e8d8bef9SDimitry Andric constexpr T // constexpr in C++14 589*e8d8bef9SDimitry Andric max(initializer_list<T> t); 5900b57cec5SDimitry Andric 5910b57cec5SDimitry Andrictemplate<class T, class Compare> 592*e8d8bef9SDimitry Andric constexpr T // constexpr in C++14 593*e8d8bef9SDimitry Andric max(initializer_list<T> t, Compare comp); 5940b57cec5SDimitry Andric 5950b57cec5SDimitry Andrictemplate<class ForwardIterator> 596*e8d8bef9SDimitry Andric constexpr pair<ForwardIterator, ForwardIterator> // constexpr in C++14 597*e8d8bef9SDimitry Andric minmax_element(ForwardIterator first, ForwardIterator last); 5980b57cec5SDimitry Andric 5990b57cec5SDimitry Andrictemplate<class ForwardIterator, class Compare> 600*e8d8bef9SDimitry Andric constexpr pair<ForwardIterator, ForwardIterator> // constexpr in C++14 601*e8d8bef9SDimitry Andric minmax_element(ForwardIterator first, ForwardIterator last, Compare comp); 6020b57cec5SDimitry Andric 6030b57cec5SDimitry Andrictemplate<class T> 604*e8d8bef9SDimitry Andric constexpr pair<const T&, const T&> // constexpr in C++14 605*e8d8bef9SDimitry Andric minmax(const T& a, const T& b); 6060b57cec5SDimitry Andric 6070b57cec5SDimitry Andrictemplate<class T, class Compare> 608*e8d8bef9SDimitry Andric constexpr pair<const T&, const T&> // constexpr in C++14 609*e8d8bef9SDimitry Andric minmax(const T& a, const T& b, Compare comp); 6100b57cec5SDimitry Andric 6110b57cec5SDimitry Andrictemplate<class T> 612*e8d8bef9SDimitry Andric constexpr pair<T, T> // constexpr in C++14 613*e8d8bef9SDimitry Andric minmax(initializer_list<T> t); 6140b57cec5SDimitry Andric 6150b57cec5SDimitry Andrictemplate<class T, class Compare> 616*e8d8bef9SDimitry Andric constexpr pair<T, T> // constexpr in C++14 617*e8d8bef9SDimitry Andric minmax(initializer_list<T> t, Compare comp); 6180b57cec5SDimitry Andric 6190b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2> 6200b57cec5SDimitry Andric constexpr bool // constexpr in C++20 6210b57cec5SDimitry Andric lexicographical_compare(InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, InputIterator2 last2); 6220b57cec5SDimitry Andric 6230b57cec5SDimitry Andrictemplate <class InputIterator1, class InputIterator2, class Compare> 6240b57cec5SDimitry Andric constexpr bool // constexpr in C++20 6250b57cec5SDimitry Andric lexicographical_compare(InputIterator1 first1, InputIterator1 last1, 6260b57cec5SDimitry Andric InputIterator2 first2, InputIterator2 last2, Compare comp); 6270b57cec5SDimitry Andric 6280b57cec5SDimitry Andrictemplate <class BidirectionalIterator> 629*e8d8bef9SDimitry Andric constexpr bool // constexpr in C++20 6300b57cec5SDimitry Andric next_permutation(BidirectionalIterator first, BidirectionalIterator last); 6310b57cec5SDimitry Andric 6320b57cec5SDimitry Andrictemplate <class BidirectionalIterator, class Compare> 633*e8d8bef9SDimitry Andric constexpr bool // constexpr in C++20 6340b57cec5SDimitry Andric next_permutation(BidirectionalIterator first, BidirectionalIterator last, Compare comp); 6350b57cec5SDimitry Andric 6360b57cec5SDimitry Andrictemplate <class BidirectionalIterator> 637*e8d8bef9SDimitry Andric constexpr bool // constexpr in C++20 6380b57cec5SDimitry Andric prev_permutation(BidirectionalIterator first, BidirectionalIterator last); 6390b57cec5SDimitry Andric 6400b57cec5SDimitry Andrictemplate <class BidirectionalIterator, class Compare> 641*e8d8bef9SDimitry Andric constexpr bool // constexpr in C++20 6420b57cec5SDimitry Andric prev_permutation(BidirectionalIterator first, BidirectionalIterator last, Compare comp); 6430b57cec5SDimitry Andric 6440b57cec5SDimitry Andric} // std 6450b57cec5SDimitry Andric 6460b57cec5SDimitry Andric*/ 6470b57cec5SDimitry Andric 6480b57cec5SDimitry Andric#include <__config> 6490b57cec5SDimitry Andric#include <initializer_list> 6500b57cec5SDimitry Andric#include <type_traits> 6510b57cec5SDimitry Andric#include <cstring> 6520b57cec5SDimitry Andric#include <utility> // needed to provide swap_ranges. 6530b57cec5SDimitry Andric#include <memory> 6540b57cec5SDimitry Andric#include <functional> 6550b57cec5SDimitry Andric#include <iterator> 6560b57cec5SDimitry Andric#include <cstddef> 6570b57cec5SDimitry Andric#include <bit> 6580b57cec5SDimitry Andric#include <version> 6590b57cec5SDimitry Andric 6600b57cec5SDimitry Andric#include <__debug> 6610b57cec5SDimitry Andric 6620b57cec5SDimitry Andric#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER) 6630b57cec5SDimitry Andric#pragma GCC system_header 6640b57cec5SDimitry Andric#endif 6650b57cec5SDimitry Andric 6660b57cec5SDimitry Andric_LIBCPP_PUSH_MACROS 6670b57cec5SDimitry Andric#include <__undef_macros> 6680b57cec5SDimitry Andric 6690b57cec5SDimitry Andric 6700b57cec5SDimitry Andric_LIBCPP_BEGIN_NAMESPACE_STD 6710b57cec5SDimitry Andric 6720b57cec5SDimitry Andric// I'd like to replace these with _VSTD::equal_to<void>, but can't because: 6730b57cec5SDimitry Andric// * That only works with C++14 and later, and 6740b57cec5SDimitry Andric// * We haven't included <functional> here. 6750b57cec5SDimitry Andrictemplate <class _T1, class _T2 = _T1> 6760b57cec5SDimitry Andricstruct __equal_to 6770b57cec5SDimitry Andric{ 6780b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 bool operator()(const _T1& __x, const _T1& __y) const {return __x == __y;} 6790b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 bool operator()(const _T1& __x, const _T2& __y) const {return __x == __y;} 6800b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 bool operator()(const _T2& __x, const _T1& __y) const {return __x == __y;} 6810b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 bool operator()(const _T2& __x, const _T2& __y) const {return __x == __y;} 6820b57cec5SDimitry Andric}; 6830b57cec5SDimitry Andric 6840b57cec5SDimitry Andrictemplate <class _T1> 6850b57cec5SDimitry Andricstruct __equal_to<_T1, _T1> 6860b57cec5SDimitry Andric{ 6870b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 6880b57cec5SDimitry Andric bool operator()(const _T1& __x, const _T1& __y) const {return __x == __y;} 6890b57cec5SDimitry Andric}; 6900b57cec5SDimitry Andric 6910b57cec5SDimitry Andrictemplate <class _T1> 6920b57cec5SDimitry Andricstruct __equal_to<const _T1, _T1> 6930b57cec5SDimitry Andric{ 6940b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 6950b57cec5SDimitry Andric bool operator()(const _T1& __x, const _T1& __y) const {return __x == __y;} 6960b57cec5SDimitry Andric}; 6970b57cec5SDimitry Andric 6980b57cec5SDimitry Andrictemplate <class _T1> 6990b57cec5SDimitry Andricstruct __equal_to<_T1, const _T1> 7000b57cec5SDimitry Andric{ 7010b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 7020b57cec5SDimitry Andric bool operator()(const _T1& __x, const _T1& __y) const {return __x == __y;} 7030b57cec5SDimitry Andric}; 7040b57cec5SDimitry Andric 7050b57cec5SDimitry Andrictemplate <class _T1, class _T2 = _T1> 7060b57cec5SDimitry Andricstruct __less 7070b57cec5SDimitry Andric{ 7080b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 7090b57cec5SDimitry Andric bool operator()(const _T1& __x, const _T1& __y) const {return __x < __y;} 7100b57cec5SDimitry Andric 7110b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 7120b57cec5SDimitry Andric bool operator()(const _T1& __x, const _T2& __y) const {return __x < __y;} 7130b57cec5SDimitry Andric 7140b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 7150b57cec5SDimitry Andric bool operator()(const _T2& __x, const _T1& __y) const {return __x < __y;} 7160b57cec5SDimitry Andric 7170b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 7180b57cec5SDimitry Andric bool operator()(const _T2& __x, const _T2& __y) const {return __x < __y;} 7190b57cec5SDimitry Andric}; 7200b57cec5SDimitry Andric 7210b57cec5SDimitry Andrictemplate <class _T1> 7220b57cec5SDimitry Andricstruct __less<_T1, _T1> 7230b57cec5SDimitry Andric{ 7240b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 7250b57cec5SDimitry Andric bool operator()(const _T1& __x, const _T1& __y) const {return __x < __y;} 7260b57cec5SDimitry Andric}; 7270b57cec5SDimitry Andric 7280b57cec5SDimitry Andrictemplate <class _T1> 7290b57cec5SDimitry Andricstruct __less<const _T1, _T1> 7300b57cec5SDimitry Andric{ 7310b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 7320b57cec5SDimitry Andric bool operator()(const _T1& __x, const _T1& __y) const {return __x < __y;} 7330b57cec5SDimitry Andric}; 7340b57cec5SDimitry Andric 7350b57cec5SDimitry Andrictemplate <class _T1> 7360b57cec5SDimitry Andricstruct __less<_T1, const _T1> 7370b57cec5SDimitry Andric{ 7380b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 7390b57cec5SDimitry Andric bool operator()(const _T1& __x, const _T1& __y) const {return __x < __y;} 7400b57cec5SDimitry Andric}; 7410b57cec5SDimitry Andric 7420b57cec5SDimitry Andrictemplate <class _Predicate> 7430b57cec5SDimitry Andricclass __invert // invert the sense of a comparison 7440b57cec5SDimitry Andric{ 7450b57cec5SDimitry Andricprivate: 7460b57cec5SDimitry Andric _Predicate __p_; 7470b57cec5SDimitry Andricpublic: 7480b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY __invert() {} 7490b57cec5SDimitry Andric 7500b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY 7510b57cec5SDimitry Andric explicit __invert(_Predicate __p) : __p_(__p) {} 7520b57cec5SDimitry Andric 7530b57cec5SDimitry Andric template <class _T1> 7540b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY 7550b57cec5SDimitry Andric bool operator()(const _T1& __x) {return !__p_(__x);} 7560b57cec5SDimitry Andric 7570b57cec5SDimitry Andric template <class _T1, class _T2> 7580b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY 7590b57cec5SDimitry Andric bool operator()(const _T1& __x, const _T2& __y) {return __p_(__y, __x);} 7600b57cec5SDimitry Andric}; 7610b57cec5SDimitry Andric 7620b57cec5SDimitry Andric// Perform division by two quickly for positive integers (llvm.org/PR39129) 7630b57cec5SDimitry Andric 7640b57cec5SDimitry Andrictemplate <typename _Integral> 7650b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR 7660b57cec5SDimitry Andrictypename enable_if 7670b57cec5SDimitry Andric< 7680b57cec5SDimitry Andric is_integral<_Integral>::value, 7690b57cec5SDimitry Andric _Integral 7700b57cec5SDimitry Andric>::type 7710b57cec5SDimitry Andric__half_positive(_Integral __value) 7720b57cec5SDimitry Andric{ 7730b57cec5SDimitry Andric return static_cast<_Integral>(static_cast<typename make_unsigned<_Integral>::type>(__value) / 2); 7740b57cec5SDimitry Andric} 7750b57cec5SDimitry Andric 7760b57cec5SDimitry Andrictemplate <typename _Tp> 7770b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR 7780b57cec5SDimitry Andrictypename enable_if 7790b57cec5SDimitry Andric< 7800b57cec5SDimitry Andric !is_integral<_Tp>::value, 7810b57cec5SDimitry Andric _Tp 7820b57cec5SDimitry Andric>::type 7830b57cec5SDimitry Andric__half_positive(_Tp __value) 7840b57cec5SDimitry Andric{ 7850b57cec5SDimitry Andric return __value / 2; 7860b57cec5SDimitry Andric} 7870b57cec5SDimitry Andric 7880b57cec5SDimitry Andric#ifdef _LIBCPP_DEBUG 7890b57cec5SDimitry Andric 7900b57cec5SDimitry Andrictemplate <class _Compare> 7910b57cec5SDimitry Andricstruct __debug_less 7920b57cec5SDimitry Andric{ 7930b57cec5SDimitry Andric _Compare &__comp_; 7940b57cec5SDimitry Andric _LIBCPP_CONSTEXPR_AFTER_CXX17 7950b57cec5SDimitry Andric __debug_less(_Compare& __c) : __comp_(__c) {} 7960b57cec5SDimitry Andric 7970b57cec5SDimitry Andric template <class _Tp, class _Up> 7980b57cec5SDimitry Andric _LIBCPP_CONSTEXPR_AFTER_CXX17 7990b57cec5SDimitry Andric bool operator()(const _Tp& __x, const _Up& __y) 8000b57cec5SDimitry Andric { 8010b57cec5SDimitry Andric bool __r = __comp_(__x, __y); 8020b57cec5SDimitry Andric if (__r) 8030b57cec5SDimitry Andric __do_compare_assert(0, __y, __x); 8040b57cec5SDimitry Andric return __r; 8050b57cec5SDimitry Andric } 8060b57cec5SDimitry Andric 8070b57cec5SDimitry Andric template <class _Tp, class _Up> 8080b57cec5SDimitry Andric _LIBCPP_CONSTEXPR_AFTER_CXX17 8090b57cec5SDimitry Andric bool operator()(_Tp& __x, _Up& __y) 8100b57cec5SDimitry Andric { 8110b57cec5SDimitry Andric bool __r = __comp_(__x, __y); 8120b57cec5SDimitry Andric if (__r) 8130b57cec5SDimitry Andric __do_compare_assert(0, __y, __x); 8140b57cec5SDimitry Andric return __r; 8150b57cec5SDimitry Andric } 8160b57cec5SDimitry Andric 8170b57cec5SDimitry Andric template <class _LHS, class _RHS> 8180b57cec5SDimitry Andric _LIBCPP_CONSTEXPR_AFTER_CXX17 8190b57cec5SDimitry Andric inline _LIBCPP_INLINE_VISIBILITY 8200b57cec5SDimitry Andric decltype((void)_VSTD::declval<_Compare&>()( 8210b57cec5SDimitry Andric _VSTD::declval<_LHS &>(), _VSTD::declval<_RHS &>())) 8220b57cec5SDimitry Andric __do_compare_assert(int, _LHS & __l, _RHS & __r) { 8230b57cec5SDimitry Andric _LIBCPP_ASSERT(!__comp_(__l, __r), 8240b57cec5SDimitry Andric "Comparator does not induce a strict weak ordering"); 8250b57cec5SDimitry Andric } 8260b57cec5SDimitry Andric 8270b57cec5SDimitry Andric template <class _LHS, class _RHS> 8280b57cec5SDimitry Andric _LIBCPP_CONSTEXPR_AFTER_CXX17 8290b57cec5SDimitry Andric inline _LIBCPP_INLINE_VISIBILITY 8300b57cec5SDimitry Andric void __do_compare_assert(long, _LHS &, _RHS &) {} 8310b57cec5SDimitry Andric}; 8320b57cec5SDimitry Andric 8330b57cec5SDimitry Andric#endif // _LIBCPP_DEBUG 8340b57cec5SDimitry Andric 8350b57cec5SDimitry Andrictemplate <class _Comp> 8360b57cec5SDimitry Andricstruct __comp_ref_type { 8370b57cec5SDimitry Andric // Pass the comparator by lvalue reference. Or in debug mode, using a 8380b57cec5SDimitry Andric // debugging wrapper that stores a reference. 8390b57cec5SDimitry Andric#ifndef _LIBCPP_DEBUG 8400b57cec5SDimitry Andric typedef typename add_lvalue_reference<_Comp>::type type; 8410b57cec5SDimitry Andric#else 8420b57cec5SDimitry Andric typedef __debug_less<_Comp> type; 8430b57cec5SDimitry Andric#endif 8440b57cec5SDimitry Andric}; 8450b57cec5SDimitry Andric 8460b57cec5SDimitry Andric// all_of 8470b57cec5SDimitry Andric 8480b57cec5SDimitry Andrictemplate <class _InputIterator, class _Predicate> 8490b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 8500b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 8510b57cec5SDimitry Andricbool 8520b57cec5SDimitry Andricall_of(_InputIterator __first, _InputIterator __last, _Predicate __pred) 8530b57cec5SDimitry Andric{ 8540b57cec5SDimitry Andric for (; __first != __last; ++__first) 8550b57cec5SDimitry Andric if (!__pred(*__first)) 8560b57cec5SDimitry Andric return false; 8570b57cec5SDimitry Andric return true; 8580b57cec5SDimitry Andric} 8590b57cec5SDimitry Andric 8600b57cec5SDimitry Andric// any_of 8610b57cec5SDimitry Andric 8620b57cec5SDimitry Andrictemplate <class _InputIterator, class _Predicate> 8630b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 8640b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 8650b57cec5SDimitry Andricbool 8660b57cec5SDimitry Andricany_of(_InputIterator __first, _InputIterator __last, _Predicate __pred) 8670b57cec5SDimitry Andric{ 8680b57cec5SDimitry Andric for (; __first != __last; ++__first) 8690b57cec5SDimitry Andric if (__pred(*__first)) 8700b57cec5SDimitry Andric return true; 8710b57cec5SDimitry Andric return false; 8720b57cec5SDimitry Andric} 8730b57cec5SDimitry Andric 8740b57cec5SDimitry Andric// none_of 8750b57cec5SDimitry Andric 8760b57cec5SDimitry Andrictemplate <class _InputIterator, class _Predicate> 8770b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 8780b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 8790b57cec5SDimitry Andricbool 8800b57cec5SDimitry Andricnone_of(_InputIterator __first, _InputIterator __last, _Predicate __pred) 8810b57cec5SDimitry Andric{ 8820b57cec5SDimitry Andric for (; __first != __last; ++__first) 8830b57cec5SDimitry Andric if (__pred(*__first)) 8840b57cec5SDimitry Andric return false; 8850b57cec5SDimitry Andric return true; 8860b57cec5SDimitry Andric} 8870b57cec5SDimitry Andric 8880b57cec5SDimitry Andric// for_each 8890b57cec5SDimitry Andric 8900b57cec5SDimitry Andrictemplate <class _InputIterator, class _Function> 8910b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 8920b57cec5SDimitry Andric_Function 8930b57cec5SDimitry Andricfor_each(_InputIterator __first, _InputIterator __last, _Function __f) 8940b57cec5SDimitry Andric{ 8950b57cec5SDimitry Andric for (; __first != __last; ++__first) 8960b57cec5SDimitry Andric __f(*__first); 8970b57cec5SDimitry Andric return __f; 8980b57cec5SDimitry Andric} 8990b57cec5SDimitry Andric 9000b57cec5SDimitry Andric#if _LIBCPP_STD_VER > 14 9010b57cec5SDimitry Andric// for_each_n 9020b57cec5SDimitry Andric 9030b57cec5SDimitry Andrictemplate <class _InputIterator, class _Size, class _Function> 9040b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 9050b57cec5SDimitry Andric_InputIterator 9060b57cec5SDimitry Andricfor_each_n(_InputIterator __first, _Size __orig_n, _Function __f) 9070b57cec5SDimitry Andric{ 908*e8d8bef9SDimitry Andric typedef decltype(_VSTD::__convert_to_integral(__orig_n)) _IntegralSize; 9090b57cec5SDimitry Andric _IntegralSize __n = __orig_n; 9100b57cec5SDimitry Andric while (__n > 0) 9110b57cec5SDimitry Andric { 9120b57cec5SDimitry Andric __f(*__first); 9130b57cec5SDimitry Andric ++__first; 9140b57cec5SDimitry Andric --__n; 9150b57cec5SDimitry Andric } 9160b57cec5SDimitry Andric return __first; 9170b57cec5SDimitry Andric} 9180b57cec5SDimitry Andric#endif 9190b57cec5SDimitry Andric 9200b57cec5SDimitry Andric// find 9210b57cec5SDimitry Andric 9220b57cec5SDimitry Andrictemplate <class _InputIterator, class _Tp> 9230b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 9240b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 9250b57cec5SDimitry Andric_InputIterator 9260b57cec5SDimitry Andricfind(_InputIterator __first, _InputIterator __last, const _Tp& __value_) 9270b57cec5SDimitry Andric{ 9280b57cec5SDimitry Andric for (; __first != __last; ++__first) 9290b57cec5SDimitry Andric if (*__first == __value_) 9300b57cec5SDimitry Andric break; 9310b57cec5SDimitry Andric return __first; 9320b57cec5SDimitry Andric} 9330b57cec5SDimitry Andric 9340b57cec5SDimitry Andric// find_if 9350b57cec5SDimitry Andric 9360b57cec5SDimitry Andrictemplate <class _InputIterator, class _Predicate> 9370b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 9380b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 9390b57cec5SDimitry Andric_InputIterator 9400b57cec5SDimitry Andricfind_if(_InputIterator __first, _InputIterator __last, _Predicate __pred) 9410b57cec5SDimitry Andric{ 9420b57cec5SDimitry Andric for (; __first != __last; ++__first) 9430b57cec5SDimitry Andric if (__pred(*__first)) 9440b57cec5SDimitry Andric break; 9450b57cec5SDimitry Andric return __first; 9460b57cec5SDimitry Andric} 9470b57cec5SDimitry Andric 9480b57cec5SDimitry Andric// find_if_not 9490b57cec5SDimitry Andric 9500b57cec5SDimitry Andrictemplate<class _InputIterator, class _Predicate> 9510b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 9520b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 9530b57cec5SDimitry Andric_InputIterator 9540b57cec5SDimitry Andricfind_if_not(_InputIterator __first, _InputIterator __last, _Predicate __pred) 9550b57cec5SDimitry Andric{ 9560b57cec5SDimitry Andric for (; __first != __last; ++__first) 9570b57cec5SDimitry Andric if (!__pred(*__first)) 9580b57cec5SDimitry Andric break; 9590b57cec5SDimitry Andric return __first; 9600b57cec5SDimitry Andric} 9610b57cec5SDimitry Andric 9620b57cec5SDimitry Andric// find_end 9630b57cec5SDimitry Andric 9640b57cec5SDimitry Andrictemplate <class _BinaryPredicate, class _ForwardIterator1, class _ForwardIterator2> 9650b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _ForwardIterator1 9660b57cec5SDimitry Andric__find_end(_ForwardIterator1 __first1, _ForwardIterator1 __last1, 9670b57cec5SDimitry Andric _ForwardIterator2 __first2, _ForwardIterator2 __last2, _BinaryPredicate __pred, 9680b57cec5SDimitry Andric forward_iterator_tag, forward_iterator_tag) 9690b57cec5SDimitry Andric{ 9700b57cec5SDimitry Andric // modeled after search algorithm 9710b57cec5SDimitry Andric _ForwardIterator1 __r = __last1; // __last1 is the "default" answer 9720b57cec5SDimitry Andric if (__first2 == __last2) 9730b57cec5SDimitry Andric return __r; 9740b57cec5SDimitry Andric while (true) 9750b57cec5SDimitry Andric { 9760b57cec5SDimitry Andric while (true) 9770b57cec5SDimitry Andric { 9780b57cec5SDimitry Andric if (__first1 == __last1) // if source exhausted return last correct answer 9790b57cec5SDimitry Andric return __r; // (or __last1 if never found) 9800b57cec5SDimitry Andric if (__pred(*__first1, *__first2)) 9810b57cec5SDimitry Andric break; 9820b57cec5SDimitry Andric ++__first1; 9830b57cec5SDimitry Andric } 9840b57cec5SDimitry Andric // *__first1 matches *__first2, now match elements after here 9850b57cec5SDimitry Andric _ForwardIterator1 __m1 = __first1; 9860b57cec5SDimitry Andric _ForwardIterator2 __m2 = __first2; 9870b57cec5SDimitry Andric while (true) 9880b57cec5SDimitry Andric { 9890b57cec5SDimitry Andric if (++__m2 == __last2) 9900b57cec5SDimitry Andric { // Pattern exhaused, record answer and search for another one 9910b57cec5SDimitry Andric __r = __first1; 9920b57cec5SDimitry Andric ++__first1; 9930b57cec5SDimitry Andric break; 9940b57cec5SDimitry Andric } 9950b57cec5SDimitry Andric if (++__m1 == __last1) // Source exhausted, return last answer 9960b57cec5SDimitry Andric return __r; 9970b57cec5SDimitry Andric if (!__pred(*__m1, *__m2)) // mismatch, restart with a new __first 9980b57cec5SDimitry Andric { 9990b57cec5SDimitry Andric ++__first1; 10000b57cec5SDimitry Andric break; 10010b57cec5SDimitry Andric } // else there is a match, check next elements 10020b57cec5SDimitry Andric } 10030b57cec5SDimitry Andric } 10040b57cec5SDimitry Andric} 10050b57cec5SDimitry Andric 10060b57cec5SDimitry Andrictemplate <class _BinaryPredicate, class _BidirectionalIterator1, class _BidirectionalIterator2> 10070b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _BidirectionalIterator1 10080b57cec5SDimitry Andric__find_end(_BidirectionalIterator1 __first1, _BidirectionalIterator1 __last1, 10090b57cec5SDimitry Andric _BidirectionalIterator2 __first2, _BidirectionalIterator2 __last2, _BinaryPredicate __pred, 10100b57cec5SDimitry Andric bidirectional_iterator_tag, bidirectional_iterator_tag) 10110b57cec5SDimitry Andric{ 10120b57cec5SDimitry Andric // modeled after search algorithm (in reverse) 10130b57cec5SDimitry Andric if (__first2 == __last2) 10140b57cec5SDimitry Andric return __last1; // Everything matches an empty sequence 10150b57cec5SDimitry Andric _BidirectionalIterator1 __l1 = __last1; 10160b57cec5SDimitry Andric _BidirectionalIterator2 __l2 = __last2; 10170b57cec5SDimitry Andric --__l2; 10180b57cec5SDimitry Andric while (true) 10190b57cec5SDimitry Andric { 10200b57cec5SDimitry Andric // Find last element in sequence 1 that matchs *(__last2-1), with a mininum of loop checks 10210b57cec5SDimitry Andric while (true) 10220b57cec5SDimitry Andric { 10230b57cec5SDimitry Andric if (__first1 == __l1) // return __last1 if no element matches *__first2 10240b57cec5SDimitry Andric return __last1; 10250b57cec5SDimitry Andric if (__pred(*--__l1, *__l2)) 10260b57cec5SDimitry Andric break; 10270b57cec5SDimitry Andric } 10280b57cec5SDimitry Andric // *__l1 matches *__l2, now match elements before here 10290b57cec5SDimitry Andric _BidirectionalIterator1 __m1 = __l1; 10300b57cec5SDimitry Andric _BidirectionalIterator2 __m2 = __l2; 10310b57cec5SDimitry Andric while (true) 10320b57cec5SDimitry Andric { 10330b57cec5SDimitry Andric if (__m2 == __first2) // If pattern exhausted, __m1 is the answer (works for 1 element pattern) 10340b57cec5SDimitry Andric return __m1; 10350b57cec5SDimitry Andric if (__m1 == __first1) // Otherwise if source exhaused, pattern not found 10360b57cec5SDimitry Andric return __last1; 10370b57cec5SDimitry Andric if (!__pred(*--__m1, *--__m2)) // if there is a mismatch, restart with a new __l1 10380b57cec5SDimitry Andric { 10390b57cec5SDimitry Andric break; 10400b57cec5SDimitry Andric } // else there is a match, check next elements 10410b57cec5SDimitry Andric } 10420b57cec5SDimitry Andric } 10430b57cec5SDimitry Andric} 10440b57cec5SDimitry Andric 10450b57cec5SDimitry Andrictemplate <class _BinaryPredicate, class _RandomAccessIterator1, class _RandomAccessIterator2> 10460b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX11 _RandomAccessIterator1 10470b57cec5SDimitry Andric__find_end(_RandomAccessIterator1 __first1, _RandomAccessIterator1 __last1, 10480b57cec5SDimitry Andric _RandomAccessIterator2 __first2, _RandomAccessIterator2 __last2, _BinaryPredicate __pred, 10490b57cec5SDimitry Andric random_access_iterator_tag, random_access_iterator_tag) 10500b57cec5SDimitry Andric{ 10510b57cec5SDimitry Andric // Take advantage of knowing source and pattern lengths. Stop short when source is smaller than pattern 10520b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator2>::difference_type __len2 = __last2 - __first2; 10530b57cec5SDimitry Andric if (__len2 == 0) 10540b57cec5SDimitry Andric return __last1; 10550b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator1>::difference_type __len1 = __last1 - __first1; 10560b57cec5SDimitry Andric if (__len1 < __len2) 10570b57cec5SDimitry Andric return __last1; 10580b57cec5SDimitry Andric const _RandomAccessIterator1 __s = __first1 + (__len2 - 1); // End of pattern match can't go before here 10590b57cec5SDimitry Andric _RandomAccessIterator1 __l1 = __last1; 10600b57cec5SDimitry Andric _RandomAccessIterator2 __l2 = __last2; 10610b57cec5SDimitry Andric --__l2; 10620b57cec5SDimitry Andric while (true) 10630b57cec5SDimitry Andric { 10640b57cec5SDimitry Andric while (true) 10650b57cec5SDimitry Andric { 10660b57cec5SDimitry Andric if (__s == __l1) 10670b57cec5SDimitry Andric return __last1; 10680b57cec5SDimitry Andric if (__pred(*--__l1, *__l2)) 10690b57cec5SDimitry Andric break; 10700b57cec5SDimitry Andric } 10710b57cec5SDimitry Andric _RandomAccessIterator1 __m1 = __l1; 10720b57cec5SDimitry Andric _RandomAccessIterator2 __m2 = __l2; 10730b57cec5SDimitry Andric while (true) 10740b57cec5SDimitry Andric { 10750b57cec5SDimitry Andric if (__m2 == __first2) 10760b57cec5SDimitry Andric return __m1; 10770b57cec5SDimitry Andric // no need to check range on __m1 because __s guarantees we have enough source 10780b57cec5SDimitry Andric if (!__pred(*--__m1, *--__m2)) 10790b57cec5SDimitry Andric { 10800b57cec5SDimitry Andric break; 10810b57cec5SDimitry Andric } 10820b57cec5SDimitry Andric } 10830b57cec5SDimitry Andric } 10840b57cec5SDimitry Andric} 10850b57cec5SDimitry Andric 10860b57cec5SDimitry Andrictemplate <class _ForwardIterator1, class _ForwardIterator2, class _BinaryPredicate> 10870b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 10880b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 10890b57cec5SDimitry Andric_ForwardIterator1 10900b57cec5SDimitry Andricfind_end(_ForwardIterator1 __first1, _ForwardIterator1 __last1, 10910b57cec5SDimitry Andric _ForwardIterator2 __first2, _ForwardIterator2 __last2, _BinaryPredicate __pred) 10920b57cec5SDimitry Andric{ 10930b57cec5SDimitry Andric return _VSTD::__find_end<typename add_lvalue_reference<_BinaryPredicate>::type> 10940b57cec5SDimitry Andric (__first1, __last1, __first2, __last2, __pred, 10950b57cec5SDimitry Andric typename iterator_traits<_ForwardIterator1>::iterator_category(), 10960b57cec5SDimitry Andric typename iterator_traits<_ForwardIterator2>::iterator_category()); 10970b57cec5SDimitry Andric} 10980b57cec5SDimitry Andric 10990b57cec5SDimitry Andrictemplate <class _ForwardIterator1, class _ForwardIterator2> 11000b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 11010b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 11020b57cec5SDimitry Andric_ForwardIterator1 11030b57cec5SDimitry Andricfind_end(_ForwardIterator1 __first1, _ForwardIterator1 __last1, 11040b57cec5SDimitry Andric _ForwardIterator2 __first2, _ForwardIterator2 __last2) 11050b57cec5SDimitry Andric{ 11060b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator1>::value_type __v1; 11070b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator2>::value_type __v2; 11080b57cec5SDimitry Andric return _VSTD::find_end(__first1, __last1, __first2, __last2, __equal_to<__v1, __v2>()); 11090b57cec5SDimitry Andric} 11100b57cec5SDimitry Andric 11110b57cec5SDimitry Andric// find_first_of 11120b57cec5SDimitry Andric 11130b57cec5SDimitry Andrictemplate <class _ForwardIterator1, class _ForwardIterator2, class _BinaryPredicate> 11140b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX11 _ForwardIterator1 11150b57cec5SDimitry Andric__find_first_of_ce(_ForwardIterator1 __first1, _ForwardIterator1 __last1, 11160b57cec5SDimitry Andric _ForwardIterator2 __first2, _ForwardIterator2 __last2, _BinaryPredicate __pred) 11170b57cec5SDimitry Andric{ 11180b57cec5SDimitry Andric for (; __first1 != __last1; ++__first1) 11190b57cec5SDimitry Andric for (_ForwardIterator2 __j = __first2; __j != __last2; ++__j) 11200b57cec5SDimitry Andric if (__pred(*__first1, *__j)) 11210b57cec5SDimitry Andric return __first1; 11220b57cec5SDimitry Andric return __last1; 11230b57cec5SDimitry Andric} 11240b57cec5SDimitry Andric 11250b57cec5SDimitry Andric 11260b57cec5SDimitry Andrictemplate <class _ForwardIterator1, class _ForwardIterator2, class _BinaryPredicate> 11270b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 11280b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 11290b57cec5SDimitry Andric_ForwardIterator1 11300b57cec5SDimitry Andricfind_first_of(_ForwardIterator1 __first1, _ForwardIterator1 __last1, 11310b57cec5SDimitry Andric _ForwardIterator2 __first2, _ForwardIterator2 __last2, _BinaryPredicate __pred) 11320b57cec5SDimitry Andric{ 11330b57cec5SDimitry Andric return _VSTD::__find_first_of_ce(__first1, __last1, __first2, __last2, __pred); 11340b57cec5SDimitry Andric} 11350b57cec5SDimitry Andric 11360b57cec5SDimitry Andrictemplate <class _ForwardIterator1, class _ForwardIterator2> 11370b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 11380b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 11390b57cec5SDimitry Andric_ForwardIterator1 11400b57cec5SDimitry Andricfind_first_of(_ForwardIterator1 __first1, _ForwardIterator1 __last1, 11410b57cec5SDimitry Andric _ForwardIterator2 __first2, _ForwardIterator2 __last2) 11420b57cec5SDimitry Andric{ 11430b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator1>::value_type __v1; 11440b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator2>::value_type __v2; 11450b57cec5SDimitry Andric return _VSTD::__find_first_of_ce(__first1, __last1, __first2, __last2, __equal_to<__v1, __v2>()); 11460b57cec5SDimitry Andric} 11470b57cec5SDimitry Andric 11480b57cec5SDimitry Andric// adjacent_find 11490b57cec5SDimitry Andric 11500b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _BinaryPredicate> 11510b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 11520b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 11530b57cec5SDimitry Andric_ForwardIterator 11540b57cec5SDimitry Andricadjacent_find(_ForwardIterator __first, _ForwardIterator __last, _BinaryPredicate __pred) 11550b57cec5SDimitry Andric{ 11560b57cec5SDimitry Andric if (__first != __last) 11570b57cec5SDimitry Andric { 11580b57cec5SDimitry Andric _ForwardIterator __i = __first; 11590b57cec5SDimitry Andric while (++__i != __last) 11600b57cec5SDimitry Andric { 11610b57cec5SDimitry Andric if (__pred(*__first, *__i)) 11620b57cec5SDimitry Andric return __first; 11630b57cec5SDimitry Andric __first = __i; 11640b57cec5SDimitry Andric } 11650b57cec5SDimitry Andric } 11660b57cec5SDimitry Andric return __last; 11670b57cec5SDimitry Andric} 11680b57cec5SDimitry Andric 11690b57cec5SDimitry Andrictemplate <class _ForwardIterator> 11700b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 11710b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 11720b57cec5SDimitry Andric_ForwardIterator 11730b57cec5SDimitry Andricadjacent_find(_ForwardIterator __first, _ForwardIterator __last) 11740b57cec5SDimitry Andric{ 11750b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator>::value_type __v; 11760b57cec5SDimitry Andric return _VSTD::adjacent_find(__first, __last, __equal_to<__v>()); 11770b57cec5SDimitry Andric} 11780b57cec5SDimitry Andric 11790b57cec5SDimitry Andric// count 11800b57cec5SDimitry Andric 11810b57cec5SDimitry Andrictemplate <class _InputIterator, class _Tp> 11820b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 11830b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 11840b57cec5SDimitry Andrictypename iterator_traits<_InputIterator>::difference_type 11850b57cec5SDimitry Andriccount(_InputIterator __first, _InputIterator __last, const _Tp& __value_) 11860b57cec5SDimitry Andric{ 11870b57cec5SDimitry Andric typename iterator_traits<_InputIterator>::difference_type __r(0); 11880b57cec5SDimitry Andric for (; __first != __last; ++__first) 11890b57cec5SDimitry Andric if (*__first == __value_) 11900b57cec5SDimitry Andric ++__r; 11910b57cec5SDimitry Andric return __r; 11920b57cec5SDimitry Andric} 11930b57cec5SDimitry Andric 11940b57cec5SDimitry Andric// count_if 11950b57cec5SDimitry Andric 11960b57cec5SDimitry Andrictemplate <class _InputIterator, class _Predicate> 11970b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 11980b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 11990b57cec5SDimitry Andrictypename iterator_traits<_InputIterator>::difference_type 12000b57cec5SDimitry Andriccount_if(_InputIterator __first, _InputIterator __last, _Predicate __pred) 12010b57cec5SDimitry Andric{ 12020b57cec5SDimitry Andric typename iterator_traits<_InputIterator>::difference_type __r(0); 12030b57cec5SDimitry Andric for (; __first != __last; ++__first) 12040b57cec5SDimitry Andric if (__pred(*__first)) 12050b57cec5SDimitry Andric ++__r; 12060b57cec5SDimitry Andric return __r; 12070b57cec5SDimitry Andric} 12080b57cec5SDimitry Andric 12090b57cec5SDimitry Andric// mismatch 12100b57cec5SDimitry Andric 12110b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _BinaryPredicate> 12120b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 12130b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 12140b57cec5SDimitry Andricpair<_InputIterator1, _InputIterator2> 12150b57cec5SDimitry Andricmismatch(_InputIterator1 __first1, _InputIterator1 __last1, 12160b57cec5SDimitry Andric _InputIterator2 __first2, _BinaryPredicate __pred) 12170b57cec5SDimitry Andric{ 12180b57cec5SDimitry Andric for (; __first1 != __last1; ++__first1, (void) ++__first2) 12190b57cec5SDimitry Andric if (!__pred(*__first1, *__first2)) 12200b57cec5SDimitry Andric break; 12210b57cec5SDimitry Andric return pair<_InputIterator1, _InputIterator2>(__first1, __first2); 12220b57cec5SDimitry Andric} 12230b57cec5SDimitry Andric 12240b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2> 12250b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 12260b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 12270b57cec5SDimitry Andricpair<_InputIterator1, _InputIterator2> 12280b57cec5SDimitry Andricmismatch(_InputIterator1 __first1, _InputIterator1 __last1, _InputIterator2 __first2) 12290b57cec5SDimitry Andric{ 12300b57cec5SDimitry Andric typedef typename iterator_traits<_InputIterator1>::value_type __v1; 12310b57cec5SDimitry Andric typedef typename iterator_traits<_InputIterator2>::value_type __v2; 12320b57cec5SDimitry Andric return _VSTD::mismatch(__first1, __last1, __first2, __equal_to<__v1, __v2>()); 12330b57cec5SDimitry Andric} 12340b57cec5SDimitry Andric 12350b57cec5SDimitry Andric#if _LIBCPP_STD_VER > 11 12360b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _BinaryPredicate> 12370b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 12380b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 12390b57cec5SDimitry Andricpair<_InputIterator1, _InputIterator2> 12400b57cec5SDimitry Andricmismatch(_InputIterator1 __first1, _InputIterator1 __last1, 12410b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, 12420b57cec5SDimitry Andric _BinaryPredicate __pred) 12430b57cec5SDimitry Andric{ 12440b57cec5SDimitry Andric for (; __first1 != __last1 && __first2 != __last2; ++__first1, (void) ++__first2) 12450b57cec5SDimitry Andric if (!__pred(*__first1, *__first2)) 12460b57cec5SDimitry Andric break; 12470b57cec5SDimitry Andric return pair<_InputIterator1, _InputIterator2>(__first1, __first2); 12480b57cec5SDimitry Andric} 12490b57cec5SDimitry Andric 12500b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2> 12510b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 12520b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 12530b57cec5SDimitry Andricpair<_InputIterator1, _InputIterator2> 12540b57cec5SDimitry Andricmismatch(_InputIterator1 __first1, _InputIterator1 __last1, 12550b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2) 12560b57cec5SDimitry Andric{ 12570b57cec5SDimitry Andric typedef typename iterator_traits<_InputIterator1>::value_type __v1; 12580b57cec5SDimitry Andric typedef typename iterator_traits<_InputIterator2>::value_type __v2; 12590b57cec5SDimitry Andric return _VSTD::mismatch(__first1, __last1, __first2, __last2, __equal_to<__v1, __v2>()); 12600b57cec5SDimitry Andric} 12610b57cec5SDimitry Andric#endif 12620b57cec5SDimitry Andric 12630b57cec5SDimitry Andric// equal 12640b57cec5SDimitry Andric 12650b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _BinaryPredicate> 12660b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 12670b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 12680b57cec5SDimitry Andricbool 12690b57cec5SDimitry Andricequal(_InputIterator1 __first1, _InputIterator1 __last1, _InputIterator2 __first2, _BinaryPredicate __pred) 12700b57cec5SDimitry Andric{ 12710b57cec5SDimitry Andric for (; __first1 != __last1; ++__first1, (void) ++__first2) 12720b57cec5SDimitry Andric if (!__pred(*__first1, *__first2)) 12730b57cec5SDimitry Andric return false; 12740b57cec5SDimitry Andric return true; 12750b57cec5SDimitry Andric} 12760b57cec5SDimitry Andric 12770b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2> 12780b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 12790b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 12800b57cec5SDimitry Andricbool 12810b57cec5SDimitry Andricequal(_InputIterator1 __first1, _InputIterator1 __last1, _InputIterator2 __first2) 12820b57cec5SDimitry Andric{ 12830b57cec5SDimitry Andric typedef typename iterator_traits<_InputIterator1>::value_type __v1; 12840b57cec5SDimitry Andric typedef typename iterator_traits<_InputIterator2>::value_type __v2; 12850b57cec5SDimitry Andric return _VSTD::equal(__first1, __last1, __first2, __equal_to<__v1, __v2>()); 12860b57cec5SDimitry Andric} 12870b57cec5SDimitry Andric 12880b57cec5SDimitry Andric#if _LIBCPP_STD_VER > 11 12890b57cec5SDimitry Andrictemplate <class _BinaryPredicate, class _InputIterator1, class _InputIterator2> 12900b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 12910b57cec5SDimitry Andricbool 12920b57cec5SDimitry Andric__equal(_InputIterator1 __first1, _InputIterator1 __last1, 12930b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _BinaryPredicate __pred, 12940b57cec5SDimitry Andric input_iterator_tag, input_iterator_tag ) 12950b57cec5SDimitry Andric{ 12960b57cec5SDimitry Andric for (; __first1 != __last1 && __first2 != __last2; ++__first1, (void) ++__first2) 12970b57cec5SDimitry Andric if (!__pred(*__first1, *__first2)) 12980b57cec5SDimitry Andric return false; 12990b57cec5SDimitry Andric return __first1 == __last1 && __first2 == __last2; 13000b57cec5SDimitry Andric} 13010b57cec5SDimitry Andric 13020b57cec5SDimitry Andrictemplate <class _BinaryPredicate, class _RandomAccessIterator1, class _RandomAccessIterator2> 13030b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 13040b57cec5SDimitry Andricbool 13050b57cec5SDimitry Andric__equal(_RandomAccessIterator1 __first1, _RandomAccessIterator1 __last1, 13060b57cec5SDimitry Andric _RandomAccessIterator2 __first2, _RandomAccessIterator2 __last2, _BinaryPredicate __pred, 13070b57cec5SDimitry Andric random_access_iterator_tag, random_access_iterator_tag ) 13080b57cec5SDimitry Andric{ 13090b57cec5SDimitry Andric if ( _VSTD::distance(__first1, __last1) != _VSTD::distance(__first2, __last2)) 13100b57cec5SDimitry Andric return false; 13110b57cec5SDimitry Andric return _VSTD::equal<_RandomAccessIterator1, _RandomAccessIterator2, 13120b57cec5SDimitry Andric typename add_lvalue_reference<_BinaryPredicate>::type> 13130b57cec5SDimitry Andric (__first1, __last1, __first2, __pred ); 13140b57cec5SDimitry Andric} 13150b57cec5SDimitry Andric 13160b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _BinaryPredicate> 13170b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 13180b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 13190b57cec5SDimitry Andricbool 13200b57cec5SDimitry Andricequal(_InputIterator1 __first1, _InputIterator1 __last1, 13210b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _BinaryPredicate __pred ) 13220b57cec5SDimitry Andric{ 13230b57cec5SDimitry Andric return _VSTD::__equal<typename add_lvalue_reference<_BinaryPredicate>::type> 13240b57cec5SDimitry Andric (__first1, __last1, __first2, __last2, __pred, 13250b57cec5SDimitry Andric typename iterator_traits<_InputIterator1>::iterator_category(), 13260b57cec5SDimitry Andric typename iterator_traits<_InputIterator2>::iterator_category()); 13270b57cec5SDimitry Andric} 13280b57cec5SDimitry Andric 13290b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2> 13300b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 13310b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 13320b57cec5SDimitry Andricbool 13330b57cec5SDimitry Andricequal(_InputIterator1 __first1, _InputIterator1 __last1, 13340b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2) 13350b57cec5SDimitry Andric{ 13360b57cec5SDimitry Andric typedef typename iterator_traits<_InputIterator1>::value_type __v1; 13370b57cec5SDimitry Andric typedef typename iterator_traits<_InputIterator2>::value_type __v2; 13380b57cec5SDimitry Andric return _VSTD::__equal(__first1, __last1, __first2, __last2, __equal_to<__v1, __v2>(), 13390b57cec5SDimitry Andric typename iterator_traits<_InputIterator1>::iterator_category(), 13400b57cec5SDimitry Andric typename iterator_traits<_InputIterator2>::iterator_category()); 13410b57cec5SDimitry Andric} 13420b57cec5SDimitry Andric#endif 13430b57cec5SDimitry Andric 13440b57cec5SDimitry Andric// is_permutation 13450b57cec5SDimitry Andric 13460b57cec5SDimitry Andrictemplate<class _ForwardIterator1, class _ForwardIterator2, class _BinaryPredicate> 13470b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT _LIBCPP_CONSTEXPR_AFTER_CXX17 bool 13480b57cec5SDimitry Andricis_permutation(_ForwardIterator1 __first1, _ForwardIterator1 __last1, 13490b57cec5SDimitry Andric _ForwardIterator2 __first2, _BinaryPredicate __pred) 13500b57cec5SDimitry Andric{ 13510b57cec5SDimitry Andric// shorten sequences as much as possible by lopping of any equal prefix 13520b57cec5SDimitry Andric for (; __first1 != __last1; ++__first1, (void) ++__first2) 13530b57cec5SDimitry Andric if (!__pred(*__first1, *__first2)) 13540b57cec5SDimitry Andric break; 13550b57cec5SDimitry Andric if (__first1 == __last1) 13560b57cec5SDimitry Andric return true; 13570b57cec5SDimitry Andric 13580b57cec5SDimitry Andric// __first1 != __last1 && *__first1 != *__first2 13590b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator1>::difference_type _D1; 13600b57cec5SDimitry Andric _D1 __l1 = _VSTD::distance(__first1, __last1); 13610b57cec5SDimitry Andric if (__l1 == _D1(1)) 13620b57cec5SDimitry Andric return false; 13630b57cec5SDimitry Andric _ForwardIterator2 __last2 = _VSTD::next(__first2, __l1); 13640b57cec5SDimitry Andric // For each element in [f1, l1) see if there are the same number of 13650b57cec5SDimitry Andric // equal elements in [f2, l2) 13660b57cec5SDimitry Andric for (_ForwardIterator1 __i = __first1; __i != __last1; ++__i) 13670b57cec5SDimitry Andric { 13680b57cec5SDimitry Andric // Have we already counted the number of *__i in [f1, l1)? 13690b57cec5SDimitry Andric _ForwardIterator1 __match = __first1; 13700b57cec5SDimitry Andric for (; __match != __i; ++__match) 13710b57cec5SDimitry Andric if (__pred(*__match, *__i)) 13720b57cec5SDimitry Andric break; 13730b57cec5SDimitry Andric if (__match == __i) { 13740b57cec5SDimitry Andric // Count number of *__i in [f2, l2) 13750b57cec5SDimitry Andric _D1 __c2 = 0; 13760b57cec5SDimitry Andric for (_ForwardIterator2 __j = __first2; __j != __last2; ++__j) 13770b57cec5SDimitry Andric if (__pred(*__i, *__j)) 13780b57cec5SDimitry Andric ++__c2; 13790b57cec5SDimitry Andric if (__c2 == 0) 13800b57cec5SDimitry Andric return false; 13810b57cec5SDimitry Andric // Count number of *__i in [__i, l1) (we can start with 1) 13820b57cec5SDimitry Andric _D1 __c1 = 1; 13830b57cec5SDimitry Andric for (_ForwardIterator1 __j = _VSTD::next(__i); __j != __last1; ++__j) 13840b57cec5SDimitry Andric if (__pred(*__i, *__j)) 13850b57cec5SDimitry Andric ++__c1; 13860b57cec5SDimitry Andric if (__c1 != __c2) 13870b57cec5SDimitry Andric return false; 13880b57cec5SDimitry Andric } 13890b57cec5SDimitry Andric } 13900b57cec5SDimitry Andric return true; 13910b57cec5SDimitry Andric} 13920b57cec5SDimitry Andric 13930b57cec5SDimitry Andrictemplate<class _ForwardIterator1, class _ForwardIterator2> 13940b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 13950b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 13960b57cec5SDimitry Andricbool 13970b57cec5SDimitry Andricis_permutation(_ForwardIterator1 __first1, _ForwardIterator1 __last1, 13980b57cec5SDimitry Andric _ForwardIterator2 __first2) 13990b57cec5SDimitry Andric{ 14000b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator1>::value_type __v1; 14010b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator2>::value_type __v2; 14020b57cec5SDimitry Andric return _VSTD::is_permutation(__first1, __last1, __first2, __equal_to<__v1, __v2>()); 14030b57cec5SDimitry Andric} 14040b57cec5SDimitry Andric 14050b57cec5SDimitry Andric#if _LIBCPP_STD_VER > 11 14060b57cec5SDimitry Andrictemplate<class _BinaryPredicate, class _ForwardIterator1, class _ForwardIterator2> 14070b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 bool 14080b57cec5SDimitry Andric__is_permutation(_ForwardIterator1 __first1, _ForwardIterator1 __last1, 14090b57cec5SDimitry Andric _ForwardIterator2 __first2, _ForwardIterator2 __last2, 14100b57cec5SDimitry Andric _BinaryPredicate __pred, 14110b57cec5SDimitry Andric forward_iterator_tag, forward_iterator_tag ) 14120b57cec5SDimitry Andric{ 14130b57cec5SDimitry Andric// shorten sequences as much as possible by lopping of any equal prefix 14140b57cec5SDimitry Andric for (; __first1 != __last1 && __first2 != __last2; ++__first1, (void) ++__first2) 14150b57cec5SDimitry Andric if (!__pred(*__first1, *__first2)) 14160b57cec5SDimitry Andric break; 14170b57cec5SDimitry Andric if (__first1 == __last1) 14180b57cec5SDimitry Andric return __first2 == __last2; 14190b57cec5SDimitry Andric else if (__first2 == __last2) 14200b57cec5SDimitry Andric return false; 14210b57cec5SDimitry Andric 14220b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator1>::difference_type _D1; 14230b57cec5SDimitry Andric _D1 __l1 = _VSTD::distance(__first1, __last1); 14240b57cec5SDimitry Andric 14250b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator2>::difference_type _D2; 14260b57cec5SDimitry Andric _D2 __l2 = _VSTD::distance(__first2, __last2); 14270b57cec5SDimitry Andric if (__l1 != __l2) 14280b57cec5SDimitry Andric return false; 14290b57cec5SDimitry Andric 14300b57cec5SDimitry Andric // For each element in [f1, l1) see if there are the same number of 14310b57cec5SDimitry Andric // equal elements in [f2, l2) 14320b57cec5SDimitry Andric for (_ForwardIterator1 __i = __first1; __i != __last1; ++__i) 14330b57cec5SDimitry Andric { 14340b57cec5SDimitry Andric // Have we already counted the number of *__i in [f1, l1)? 14350b57cec5SDimitry Andric _ForwardIterator1 __match = __first1; 14360b57cec5SDimitry Andric for (; __match != __i; ++__match) 14370b57cec5SDimitry Andric if (__pred(*__match, *__i)) 14380b57cec5SDimitry Andric break; 14390b57cec5SDimitry Andric if (__match == __i) { 14400b57cec5SDimitry Andric // Count number of *__i in [f2, l2) 14410b57cec5SDimitry Andric _D1 __c2 = 0; 14420b57cec5SDimitry Andric for (_ForwardIterator2 __j = __first2; __j != __last2; ++__j) 14430b57cec5SDimitry Andric if (__pred(*__i, *__j)) 14440b57cec5SDimitry Andric ++__c2; 14450b57cec5SDimitry Andric if (__c2 == 0) 14460b57cec5SDimitry Andric return false; 14470b57cec5SDimitry Andric // Count number of *__i in [__i, l1) (we can start with 1) 14480b57cec5SDimitry Andric _D1 __c1 = 1; 14490b57cec5SDimitry Andric for (_ForwardIterator1 __j = _VSTD::next(__i); __j != __last1; ++__j) 14500b57cec5SDimitry Andric if (__pred(*__i, *__j)) 14510b57cec5SDimitry Andric ++__c1; 14520b57cec5SDimitry Andric if (__c1 != __c2) 14530b57cec5SDimitry Andric return false; 14540b57cec5SDimitry Andric } 14550b57cec5SDimitry Andric } 14560b57cec5SDimitry Andric return true; 14570b57cec5SDimitry Andric} 14580b57cec5SDimitry Andric 14590b57cec5SDimitry Andrictemplate<class _BinaryPredicate, class _RandomAccessIterator1, class _RandomAccessIterator2> 14600b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 bool 14610b57cec5SDimitry Andric__is_permutation(_RandomAccessIterator1 __first1, _RandomAccessIterator2 __last1, 14620b57cec5SDimitry Andric _RandomAccessIterator1 __first2, _RandomAccessIterator2 __last2, 14630b57cec5SDimitry Andric _BinaryPredicate __pred, 14640b57cec5SDimitry Andric random_access_iterator_tag, random_access_iterator_tag ) 14650b57cec5SDimitry Andric{ 14660b57cec5SDimitry Andric if ( _VSTD::distance(__first1, __last1) != _VSTD::distance(__first2, __last2)) 14670b57cec5SDimitry Andric return false; 14680b57cec5SDimitry Andric return _VSTD::is_permutation<_RandomAccessIterator1, _RandomAccessIterator2, 14690b57cec5SDimitry Andric typename add_lvalue_reference<_BinaryPredicate>::type> 14700b57cec5SDimitry Andric (__first1, __last1, __first2, __pred ); 14710b57cec5SDimitry Andric} 14720b57cec5SDimitry Andric 14730b57cec5SDimitry Andrictemplate<class _ForwardIterator1, class _ForwardIterator2, class _BinaryPredicate> 14740b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 14750b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 14760b57cec5SDimitry Andricbool 14770b57cec5SDimitry Andricis_permutation(_ForwardIterator1 __first1, _ForwardIterator1 __last1, 14780b57cec5SDimitry Andric _ForwardIterator2 __first2, _ForwardIterator2 __last2, 14790b57cec5SDimitry Andric _BinaryPredicate __pred ) 14800b57cec5SDimitry Andric{ 14810b57cec5SDimitry Andric return _VSTD::__is_permutation<typename add_lvalue_reference<_BinaryPredicate>::type> 14820b57cec5SDimitry Andric (__first1, __last1, __first2, __last2, __pred, 14830b57cec5SDimitry Andric typename iterator_traits<_ForwardIterator1>::iterator_category(), 14840b57cec5SDimitry Andric typename iterator_traits<_ForwardIterator2>::iterator_category()); 14850b57cec5SDimitry Andric} 14860b57cec5SDimitry Andric 14870b57cec5SDimitry Andrictemplate<class _ForwardIterator1, class _ForwardIterator2> 14880b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 14890b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 14900b57cec5SDimitry Andricbool 14910b57cec5SDimitry Andricis_permutation(_ForwardIterator1 __first1, _ForwardIterator1 __last1, 14920b57cec5SDimitry Andric _ForwardIterator2 __first2, _ForwardIterator2 __last2) 14930b57cec5SDimitry Andric{ 14940b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator1>::value_type __v1; 14950b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator2>::value_type __v2; 14960b57cec5SDimitry Andric return _VSTD::__is_permutation(__first1, __last1, __first2, __last2, 14970b57cec5SDimitry Andric __equal_to<__v1, __v2>(), 14980b57cec5SDimitry Andric typename iterator_traits<_ForwardIterator1>::iterator_category(), 14990b57cec5SDimitry Andric typename iterator_traits<_ForwardIterator2>::iterator_category()); 15000b57cec5SDimitry Andric} 15010b57cec5SDimitry Andric#endif 15020b57cec5SDimitry Andric 15030b57cec5SDimitry Andric// search 15040b57cec5SDimitry Andric// __search is in <functional> 15050b57cec5SDimitry Andric 15060b57cec5SDimitry Andrictemplate <class _ForwardIterator1, class _ForwardIterator2, class _BinaryPredicate> 15070b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 15080b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 15090b57cec5SDimitry Andric_ForwardIterator1 15100b57cec5SDimitry Andricsearch(_ForwardIterator1 __first1, _ForwardIterator1 __last1, 15110b57cec5SDimitry Andric _ForwardIterator2 __first2, _ForwardIterator2 __last2, _BinaryPredicate __pred) 15120b57cec5SDimitry Andric{ 15130b57cec5SDimitry Andric return _VSTD::__search<typename add_lvalue_reference<_BinaryPredicate>::type> 15140b57cec5SDimitry Andric (__first1, __last1, __first2, __last2, __pred, 15150b57cec5SDimitry Andric typename iterator_traits<_ForwardIterator1>::iterator_category(), 15160b57cec5SDimitry Andric typename iterator_traits<_ForwardIterator2>::iterator_category()) 15170b57cec5SDimitry Andric .first; 15180b57cec5SDimitry Andric} 15190b57cec5SDimitry Andric 15200b57cec5SDimitry Andrictemplate <class _ForwardIterator1, class _ForwardIterator2> 15210b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 15220b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 15230b57cec5SDimitry Andric_ForwardIterator1 15240b57cec5SDimitry Andricsearch(_ForwardIterator1 __first1, _ForwardIterator1 __last1, 15250b57cec5SDimitry Andric _ForwardIterator2 __first2, _ForwardIterator2 __last2) 15260b57cec5SDimitry Andric{ 15270b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator1>::value_type __v1; 15280b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator2>::value_type __v2; 15290b57cec5SDimitry Andric return _VSTD::search(__first1, __last1, __first2, __last2, __equal_to<__v1, __v2>()); 15300b57cec5SDimitry Andric} 15310b57cec5SDimitry Andric 15320b57cec5SDimitry Andric 15330b57cec5SDimitry Andric#if _LIBCPP_STD_VER > 14 15340b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Searcher> 15350b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 15360b57cec5SDimitry Andric_ForwardIterator search(_ForwardIterator __f, _ForwardIterator __l, const _Searcher &__s) 15370b57cec5SDimitry Andric{ return __s(__f, __l).first; } 15380b57cec5SDimitry Andric#endif 15390b57cec5SDimitry Andric 15400b57cec5SDimitry Andric// search_n 15410b57cec5SDimitry Andric 15420b57cec5SDimitry Andrictemplate <class _BinaryPredicate, class _ForwardIterator, class _Size, class _Tp> 15430b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _ForwardIterator 15440b57cec5SDimitry Andric__search_n(_ForwardIterator __first, _ForwardIterator __last, 15450b57cec5SDimitry Andric _Size __count, const _Tp& __value_, _BinaryPredicate __pred, forward_iterator_tag) 15460b57cec5SDimitry Andric{ 15470b57cec5SDimitry Andric if (__count <= 0) 15480b57cec5SDimitry Andric return __first; 15490b57cec5SDimitry Andric while (true) 15500b57cec5SDimitry Andric { 15510b57cec5SDimitry Andric // Find first element in sequence that matchs __value_, with a mininum of loop checks 15520b57cec5SDimitry Andric while (true) 15530b57cec5SDimitry Andric { 15540b57cec5SDimitry Andric if (__first == __last) // return __last if no element matches __value_ 15550b57cec5SDimitry Andric return __last; 15560b57cec5SDimitry Andric if (__pred(*__first, __value_)) 15570b57cec5SDimitry Andric break; 15580b57cec5SDimitry Andric ++__first; 15590b57cec5SDimitry Andric } 15600b57cec5SDimitry Andric // *__first matches __value_, now match elements after here 15610b57cec5SDimitry Andric _ForwardIterator __m = __first; 15620b57cec5SDimitry Andric _Size __c(0); 15630b57cec5SDimitry Andric while (true) 15640b57cec5SDimitry Andric { 15650b57cec5SDimitry Andric if (++__c == __count) // If pattern exhausted, __first is the answer (works for 1 element pattern) 15660b57cec5SDimitry Andric return __first; 15670b57cec5SDimitry Andric if (++__m == __last) // Otherwise if source exhaused, pattern not found 15680b57cec5SDimitry Andric return __last; 15690b57cec5SDimitry Andric if (!__pred(*__m, __value_)) // if there is a mismatch, restart with a new __first 15700b57cec5SDimitry Andric { 15710b57cec5SDimitry Andric __first = __m; 15720b57cec5SDimitry Andric ++__first; 15730b57cec5SDimitry Andric break; 15740b57cec5SDimitry Andric } // else there is a match, check next elements 15750b57cec5SDimitry Andric } 15760b57cec5SDimitry Andric } 15770b57cec5SDimitry Andric} 15780b57cec5SDimitry Andric 15790b57cec5SDimitry Andrictemplate <class _BinaryPredicate, class _RandomAccessIterator, class _Size, class _Tp> 15800b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _RandomAccessIterator 15810b57cec5SDimitry Andric__search_n(_RandomAccessIterator __first, _RandomAccessIterator __last, 15820b57cec5SDimitry Andric _Size __count, const _Tp& __value_, _BinaryPredicate __pred, random_access_iterator_tag) 15830b57cec5SDimitry Andric{ 15840b57cec5SDimitry Andric if (__count <= 0) 15850b57cec5SDimitry Andric return __first; 15860b57cec5SDimitry Andric _Size __len = static_cast<_Size>(__last - __first); 15870b57cec5SDimitry Andric if (__len < __count) 15880b57cec5SDimitry Andric return __last; 15890b57cec5SDimitry Andric const _RandomAccessIterator __s = __last - (__count - 1); // Start of pattern match can't go beyond here 15900b57cec5SDimitry Andric while (true) 15910b57cec5SDimitry Andric { 15920b57cec5SDimitry Andric // Find first element in sequence that matchs __value_, with a mininum of loop checks 15930b57cec5SDimitry Andric while (true) 15940b57cec5SDimitry Andric { 15950b57cec5SDimitry Andric if (__first >= __s) // return __last if no element matches __value_ 15960b57cec5SDimitry Andric return __last; 15970b57cec5SDimitry Andric if (__pred(*__first, __value_)) 15980b57cec5SDimitry Andric break; 15990b57cec5SDimitry Andric ++__first; 16000b57cec5SDimitry Andric } 16010b57cec5SDimitry Andric // *__first matches __value_, now match elements after here 16020b57cec5SDimitry Andric _RandomAccessIterator __m = __first; 16030b57cec5SDimitry Andric _Size __c(0); 16040b57cec5SDimitry Andric while (true) 16050b57cec5SDimitry Andric { 16060b57cec5SDimitry Andric if (++__c == __count) // If pattern exhausted, __first is the answer (works for 1 element pattern) 16070b57cec5SDimitry Andric return __first; 16080b57cec5SDimitry Andric ++__m; // no need to check range on __m because __s guarantees we have enough source 16090b57cec5SDimitry Andric if (!__pred(*__m, __value_)) // if there is a mismatch, restart with a new __first 16100b57cec5SDimitry Andric { 16110b57cec5SDimitry Andric __first = __m; 16120b57cec5SDimitry Andric ++__first; 16130b57cec5SDimitry Andric break; 16140b57cec5SDimitry Andric } // else there is a match, check next elements 16150b57cec5SDimitry Andric } 16160b57cec5SDimitry Andric } 16170b57cec5SDimitry Andric} 16180b57cec5SDimitry Andric 16190b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Size, class _Tp, class _BinaryPredicate> 16200b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 16210b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 16220b57cec5SDimitry Andric_ForwardIterator 16230b57cec5SDimitry Andricsearch_n(_ForwardIterator __first, _ForwardIterator __last, 16240b57cec5SDimitry Andric _Size __count, const _Tp& __value_, _BinaryPredicate __pred) 16250b57cec5SDimitry Andric{ 16260b57cec5SDimitry Andric return _VSTD::__search_n<typename add_lvalue_reference<_BinaryPredicate>::type> 1627*e8d8bef9SDimitry Andric (__first, __last, _VSTD::__convert_to_integral(__count), __value_, __pred, 16280b57cec5SDimitry Andric typename iterator_traits<_ForwardIterator>::iterator_category()); 16290b57cec5SDimitry Andric} 16300b57cec5SDimitry Andric 16310b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Size, class _Tp> 16320b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 16330b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 16340b57cec5SDimitry Andric_ForwardIterator 16350b57cec5SDimitry Andricsearch_n(_ForwardIterator __first, _ForwardIterator __last, _Size __count, const _Tp& __value_) 16360b57cec5SDimitry Andric{ 16370b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator>::value_type __v; 1638*e8d8bef9SDimitry Andric return _VSTD::search_n(__first, __last, _VSTD::__convert_to_integral(__count), 16390b57cec5SDimitry Andric __value_, __equal_to<__v, _Tp>()); 16400b57cec5SDimitry Andric} 16410b57cec5SDimitry Andric 16420b57cec5SDimitry Andric// copy 16430b57cec5SDimitry Andrictemplate <class _Iter> 1644*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR 16450b57cec5SDimitry Andric_Iter 16460b57cec5SDimitry Andric__unwrap_iter(_Iter __i) 16470b57cec5SDimitry Andric{ 16480b57cec5SDimitry Andric return __i; 16490b57cec5SDimitry Andric} 16500b57cec5SDimitry Andric 16510b57cec5SDimitry Andrictemplate <class _Tp> 1652*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR 16530b57cec5SDimitry Andrictypename enable_if 16540b57cec5SDimitry Andric< 16550b57cec5SDimitry Andric is_trivially_copy_assignable<_Tp>::value, 16560b57cec5SDimitry Andric _Tp* 16570b57cec5SDimitry Andric>::type 16580b57cec5SDimitry Andric__unwrap_iter(move_iterator<_Tp*> __i) 16590b57cec5SDimitry Andric{ 16600b57cec5SDimitry Andric return __i.base(); 16610b57cec5SDimitry Andric} 16620b57cec5SDimitry Andric 16630b57cec5SDimitry Andric#if _LIBCPP_DEBUG_LEVEL < 2 16640b57cec5SDimitry Andric 16650b57cec5SDimitry Andrictemplate <class _Tp> 1666*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR 16670b57cec5SDimitry Andrictypename enable_if 16680b57cec5SDimitry Andric< 16690b57cec5SDimitry Andric is_trivially_copy_assignable<_Tp>::value, 16700b57cec5SDimitry Andric _Tp* 16710b57cec5SDimitry Andric>::type 16720b57cec5SDimitry Andric__unwrap_iter(__wrap_iter<_Tp*> __i) 16730b57cec5SDimitry Andric{ 16740b57cec5SDimitry Andric return __i.base(); 16750b57cec5SDimitry Andric} 16760b57cec5SDimitry Andric 16770b57cec5SDimitry Andrictemplate <class _Tp> 1678*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR 16790b57cec5SDimitry Andrictypename enable_if 16800b57cec5SDimitry Andric< 16810b57cec5SDimitry Andric is_trivially_copy_assignable<_Tp>::value, 16820b57cec5SDimitry Andric const _Tp* 16830b57cec5SDimitry Andric>::type 16840b57cec5SDimitry Andric__unwrap_iter(__wrap_iter<const _Tp*> __i) 16850b57cec5SDimitry Andric{ 16860b57cec5SDimitry Andric return __i.base(); 16870b57cec5SDimitry Andric} 16880b57cec5SDimitry Andric 16890b57cec5SDimitry Andric#else 16900b57cec5SDimitry Andric 16910b57cec5SDimitry Andrictemplate <class _Tp> 1692*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR 16930b57cec5SDimitry Andrictypename enable_if 16940b57cec5SDimitry Andric< 16950b57cec5SDimitry Andric is_trivially_copy_assignable<_Tp>::value, 16960b57cec5SDimitry Andric __wrap_iter<_Tp*> 16970b57cec5SDimitry Andric>::type 16980b57cec5SDimitry Andric__unwrap_iter(__wrap_iter<_Tp*> __i) 16990b57cec5SDimitry Andric{ 17000b57cec5SDimitry Andric return __i; 17010b57cec5SDimitry Andric} 17020b57cec5SDimitry Andric 17030b57cec5SDimitry Andric#endif // _LIBCPP_DEBUG_LEVEL < 2 17040b57cec5SDimitry Andric 17050b57cec5SDimitry Andrictemplate <class _InputIterator, class _OutputIterator> 1706480093f4SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 17070b57cec5SDimitry Andric_OutputIterator 1708480093f4SDimitry Andric__copy_constexpr(_InputIterator __first, _InputIterator __last, _OutputIterator __result) 17090b57cec5SDimitry Andric{ 17100b57cec5SDimitry Andric for (; __first != __last; ++__first, (void) ++__result) 17110b57cec5SDimitry Andric *__result = *__first; 17120b57cec5SDimitry Andric return __result; 17130b57cec5SDimitry Andric} 17140b57cec5SDimitry Andric 1715480093f4SDimitry Andrictemplate <class _InputIterator, class _OutputIterator> 1716480093f4SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 1717480093f4SDimitry Andric_OutputIterator 1718480093f4SDimitry Andric__copy(_InputIterator __first, _InputIterator __last, _OutputIterator __result) 1719480093f4SDimitry Andric{ 1720*e8d8bef9SDimitry Andric return _VSTD::__copy_constexpr(__first, __last, __result); 1721480093f4SDimitry Andric} 1722480093f4SDimitry Andric 17230b57cec5SDimitry Andrictemplate <class _Tp, class _Up> 17240b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 17250b57cec5SDimitry Andrictypename enable_if 17260b57cec5SDimitry Andric< 17270b57cec5SDimitry Andric is_same<typename remove_const<_Tp>::type, _Up>::value && 17280b57cec5SDimitry Andric is_trivially_copy_assignable<_Up>::value, 17290b57cec5SDimitry Andric _Up* 17300b57cec5SDimitry Andric>::type 17310b57cec5SDimitry Andric__copy(_Tp* __first, _Tp* __last, _Up* __result) 17320b57cec5SDimitry Andric{ 17330b57cec5SDimitry Andric const size_t __n = static_cast<size_t>(__last - __first); 17340b57cec5SDimitry Andric if (__n > 0) 17350b57cec5SDimitry Andric _VSTD::memmove(__result, __first, __n * sizeof(_Up)); 17360b57cec5SDimitry Andric return __result + __n; 17370b57cec5SDimitry Andric} 17380b57cec5SDimitry Andric 17390b57cec5SDimitry Andrictemplate <class _InputIterator, class _OutputIterator> 1740*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 17410b57cec5SDimitry Andric_OutputIterator 17420b57cec5SDimitry Andriccopy(_InputIterator __first, _InputIterator __last, _OutputIterator __result) 17430b57cec5SDimitry Andric{ 1744480093f4SDimitry Andric if (__libcpp_is_constant_evaluated()) { 1745480093f4SDimitry Andric return _VSTD::__copy_constexpr( 1746*e8d8bef9SDimitry Andric _VSTD::__unwrap_iter(__first), _VSTD::__unwrap_iter(__last), _VSTD::__unwrap_iter(__result)); 1747480093f4SDimitry Andric } else { 1748480093f4SDimitry Andric return _VSTD::__copy( 1749*e8d8bef9SDimitry Andric _VSTD::__unwrap_iter(__first), _VSTD::__unwrap_iter(__last), _VSTD::__unwrap_iter(__result)); 1750480093f4SDimitry Andric } 17510b57cec5SDimitry Andric} 17520b57cec5SDimitry Andric 17530b57cec5SDimitry Andric// copy_backward 17540b57cec5SDimitry Andric 17550b57cec5SDimitry Andrictemplate <class _BidirectionalIterator, class _OutputIterator> 1756480093f4SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 1757480093f4SDimitry Andric_OutputIterator 1758480093f4SDimitry Andric__copy_backward_constexpr(_BidirectionalIterator __first, _BidirectionalIterator __last, _OutputIterator __result) 1759480093f4SDimitry Andric{ 1760480093f4SDimitry Andric while (__first != __last) 1761480093f4SDimitry Andric *--__result = *--__last; 1762480093f4SDimitry Andric return __result; 1763480093f4SDimitry Andric} 1764480093f4SDimitry Andric 1765480093f4SDimitry Andrictemplate <class _BidirectionalIterator, class _OutputIterator> 17660b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 17670b57cec5SDimitry Andric_OutputIterator 17680b57cec5SDimitry Andric__copy_backward(_BidirectionalIterator __first, _BidirectionalIterator __last, _OutputIterator __result) 17690b57cec5SDimitry Andric{ 1770*e8d8bef9SDimitry Andric return _VSTD::__copy_backward_constexpr(__first, __last, __result); 17710b57cec5SDimitry Andric} 17720b57cec5SDimitry Andric 17730b57cec5SDimitry Andrictemplate <class _Tp, class _Up> 17740b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 17750b57cec5SDimitry Andrictypename enable_if 17760b57cec5SDimitry Andric< 17770b57cec5SDimitry Andric is_same<typename remove_const<_Tp>::type, _Up>::value && 17780b57cec5SDimitry Andric is_trivially_copy_assignable<_Up>::value, 17790b57cec5SDimitry Andric _Up* 17800b57cec5SDimitry Andric>::type 17810b57cec5SDimitry Andric__copy_backward(_Tp* __first, _Tp* __last, _Up* __result) 17820b57cec5SDimitry Andric{ 17830b57cec5SDimitry Andric const size_t __n = static_cast<size_t>(__last - __first); 17840b57cec5SDimitry Andric if (__n > 0) 17850b57cec5SDimitry Andric { 17860b57cec5SDimitry Andric __result -= __n; 17870b57cec5SDimitry Andric _VSTD::memmove(__result, __first, __n * sizeof(_Up)); 17880b57cec5SDimitry Andric } 17890b57cec5SDimitry Andric return __result; 17900b57cec5SDimitry Andric} 17910b57cec5SDimitry Andric 17920b57cec5SDimitry Andrictemplate <class _BidirectionalIterator1, class _BidirectionalIterator2> 1793*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 17940b57cec5SDimitry Andric_BidirectionalIterator2 17950b57cec5SDimitry Andriccopy_backward(_BidirectionalIterator1 __first, _BidirectionalIterator1 __last, 17960b57cec5SDimitry Andric _BidirectionalIterator2 __result) 17970b57cec5SDimitry Andric{ 1798480093f4SDimitry Andric if (__libcpp_is_constant_evaluated()) { 1799*e8d8bef9SDimitry Andric return _VSTD::__copy_backward_constexpr(_VSTD::__unwrap_iter(__first), 1800*e8d8bef9SDimitry Andric _VSTD::__unwrap_iter(__last), 1801*e8d8bef9SDimitry Andric _VSTD::__unwrap_iter(__result)); 1802480093f4SDimitry Andric } else { 1803*e8d8bef9SDimitry Andric return _VSTD::__copy_backward(_VSTD::__unwrap_iter(__first), 1804*e8d8bef9SDimitry Andric _VSTD::__unwrap_iter(__last), 1805*e8d8bef9SDimitry Andric _VSTD::__unwrap_iter(__result)); 18060b57cec5SDimitry Andric } 1807480093f4SDimitry Andric} 18080b57cec5SDimitry Andric 18090b57cec5SDimitry Andric// copy_if 18100b57cec5SDimitry Andric 18110b57cec5SDimitry Andrictemplate<class _InputIterator, class _OutputIterator, class _Predicate> 1812480093f4SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 18130b57cec5SDimitry Andric_OutputIterator 18140b57cec5SDimitry Andriccopy_if(_InputIterator __first, _InputIterator __last, 18150b57cec5SDimitry Andric _OutputIterator __result, _Predicate __pred) 18160b57cec5SDimitry Andric{ 18170b57cec5SDimitry Andric for (; __first != __last; ++__first) 18180b57cec5SDimitry Andric { 18190b57cec5SDimitry Andric if (__pred(*__first)) 18200b57cec5SDimitry Andric { 18210b57cec5SDimitry Andric *__result = *__first; 18220b57cec5SDimitry Andric ++__result; 18230b57cec5SDimitry Andric } 18240b57cec5SDimitry Andric } 18250b57cec5SDimitry Andric return __result; 18260b57cec5SDimitry Andric} 18270b57cec5SDimitry Andric 18280b57cec5SDimitry Andric// copy_n 18290b57cec5SDimitry Andric 18300b57cec5SDimitry Andrictemplate<class _InputIterator, class _Size, class _OutputIterator> 1831*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 18320b57cec5SDimitry Andrictypename enable_if 18330b57cec5SDimitry Andric< 1834480093f4SDimitry Andric __is_cpp17_input_iterator<_InputIterator>::value && 1835480093f4SDimitry Andric !__is_cpp17_random_access_iterator<_InputIterator>::value, 18360b57cec5SDimitry Andric _OutputIterator 18370b57cec5SDimitry Andric>::type 18380b57cec5SDimitry Andriccopy_n(_InputIterator __first, _Size __orig_n, _OutputIterator __result) 18390b57cec5SDimitry Andric{ 1840*e8d8bef9SDimitry Andric typedef decltype(_VSTD::__convert_to_integral(__orig_n)) _IntegralSize; 18410b57cec5SDimitry Andric _IntegralSize __n = __orig_n; 18420b57cec5SDimitry Andric if (__n > 0) 18430b57cec5SDimitry Andric { 18440b57cec5SDimitry Andric *__result = *__first; 18450b57cec5SDimitry Andric ++__result; 18460b57cec5SDimitry Andric for (--__n; __n > 0; --__n) 18470b57cec5SDimitry Andric { 18480b57cec5SDimitry Andric ++__first; 18490b57cec5SDimitry Andric *__result = *__first; 18500b57cec5SDimitry Andric ++__result; 18510b57cec5SDimitry Andric } 18520b57cec5SDimitry Andric } 18530b57cec5SDimitry Andric return __result; 18540b57cec5SDimitry Andric} 18550b57cec5SDimitry Andric 18560b57cec5SDimitry Andrictemplate<class _InputIterator, class _Size, class _OutputIterator> 1857*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 18580b57cec5SDimitry Andrictypename enable_if 18590b57cec5SDimitry Andric< 1860480093f4SDimitry Andric __is_cpp17_random_access_iterator<_InputIterator>::value, 18610b57cec5SDimitry Andric _OutputIterator 18620b57cec5SDimitry Andric>::type 18630b57cec5SDimitry Andriccopy_n(_InputIterator __first, _Size __orig_n, _OutputIterator __result) 18640b57cec5SDimitry Andric{ 1865*e8d8bef9SDimitry Andric typedef decltype(_VSTD::__convert_to_integral(__orig_n)) _IntegralSize; 18660b57cec5SDimitry Andric _IntegralSize __n = __orig_n; 18670b57cec5SDimitry Andric return _VSTD::copy(__first, __first + __n, __result); 18680b57cec5SDimitry Andric} 18690b57cec5SDimitry Andric 18700b57cec5SDimitry Andric// move 18710b57cec5SDimitry Andric 1872*e8d8bef9SDimitry Andric// __move_constexpr exists so that __move doesn't call itself when delegating to the constexpr 1873*e8d8bef9SDimitry Andric// version of __move. 18740b57cec5SDimitry Andrictemplate <class _InputIterator, class _OutputIterator> 1875*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14 18760b57cec5SDimitry Andric_OutputIterator 1877*e8d8bef9SDimitry Andric__move_constexpr(_InputIterator __first, _InputIterator __last, _OutputIterator __result) 18780b57cec5SDimitry Andric{ 18790b57cec5SDimitry Andric for (; __first != __last; ++__first, (void) ++__result) 18800b57cec5SDimitry Andric *__result = _VSTD::move(*__first); 18810b57cec5SDimitry Andric return __result; 18820b57cec5SDimitry Andric} 18830b57cec5SDimitry Andric 1884*e8d8bef9SDimitry Andrictemplate <class _InputIterator, class _OutputIterator> 1885*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14 1886*e8d8bef9SDimitry Andric_OutputIterator 1887*e8d8bef9SDimitry Andric__move(_InputIterator __first, _InputIterator __last, _OutputIterator __result) 1888*e8d8bef9SDimitry Andric{ 1889*e8d8bef9SDimitry Andric return _VSTD::__move_constexpr(__first, __last, __result); 1890*e8d8bef9SDimitry Andric} 1891*e8d8bef9SDimitry Andric 18920b57cec5SDimitry Andrictemplate <class _Tp, class _Up> 1893*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14 18940b57cec5SDimitry Andrictypename enable_if 18950b57cec5SDimitry Andric< 18960b57cec5SDimitry Andric is_same<typename remove_const<_Tp>::type, _Up>::value && 18970b57cec5SDimitry Andric is_trivially_copy_assignable<_Up>::value, 18980b57cec5SDimitry Andric _Up* 18990b57cec5SDimitry Andric>::type 19000b57cec5SDimitry Andric__move(_Tp* __first, _Tp* __last, _Up* __result) 19010b57cec5SDimitry Andric{ 1902*e8d8bef9SDimitry Andric if (__libcpp_is_constant_evaluated()) 1903*e8d8bef9SDimitry Andric return _VSTD::__move_constexpr(__first, __last, __result); 19040b57cec5SDimitry Andric const size_t __n = static_cast<size_t>(__last - __first); 19050b57cec5SDimitry Andric if (__n > 0) 19060b57cec5SDimitry Andric _VSTD::memmove(__result, __first, __n * sizeof(_Up)); 19070b57cec5SDimitry Andric return __result + __n; 19080b57cec5SDimitry Andric} 19090b57cec5SDimitry Andric 19100b57cec5SDimitry Andrictemplate <class _InputIterator, class _OutputIterator> 1911*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 19120b57cec5SDimitry Andric_OutputIterator 19130b57cec5SDimitry Andricmove(_InputIterator __first, _InputIterator __last, _OutputIterator __result) 19140b57cec5SDimitry Andric{ 1915*e8d8bef9SDimitry Andric return _VSTD::__move(_VSTD::__unwrap_iter(__first), _VSTD::__unwrap_iter(__last), _VSTD::__unwrap_iter(__result)); 19160b57cec5SDimitry Andric} 19170b57cec5SDimitry Andric 19180b57cec5SDimitry Andric// move_backward 19190b57cec5SDimitry Andric 1920*e8d8bef9SDimitry Andric// __move_backward_constexpr exists so that __move_backward doesn't call itself when delegating to 1921*e8d8bef9SDimitry Andric// the constexpr version of __move_backward. 19220b57cec5SDimitry Andrictemplate <class _InputIterator, class _OutputIterator> 1923*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14 19240b57cec5SDimitry Andric_OutputIterator 1925*e8d8bef9SDimitry Andric__move_backward_constexpr(_InputIterator __first, _InputIterator __last, _OutputIterator __result) 19260b57cec5SDimitry Andric{ 19270b57cec5SDimitry Andric while (__first != __last) 19280b57cec5SDimitry Andric *--__result = _VSTD::move(*--__last); 19290b57cec5SDimitry Andric return __result; 19300b57cec5SDimitry Andric} 19310b57cec5SDimitry Andric 1932*e8d8bef9SDimitry Andrictemplate <class _InputIterator, class _OutputIterator> 1933*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14 1934*e8d8bef9SDimitry Andric_OutputIterator 1935*e8d8bef9SDimitry Andric__move_backward(_InputIterator __first, _InputIterator __last, _OutputIterator __result) 1936*e8d8bef9SDimitry Andric{ 1937*e8d8bef9SDimitry Andric return _VSTD::__move_backward_constexpr(__first, __last, __result); 1938*e8d8bef9SDimitry Andric} 1939*e8d8bef9SDimitry Andric 19400b57cec5SDimitry Andrictemplate <class _Tp, class _Up> 1941*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14 19420b57cec5SDimitry Andrictypename enable_if 19430b57cec5SDimitry Andric< 19440b57cec5SDimitry Andric is_same<typename remove_const<_Tp>::type, _Up>::value && 19450b57cec5SDimitry Andric is_trivially_copy_assignable<_Up>::value, 19460b57cec5SDimitry Andric _Up* 19470b57cec5SDimitry Andric>::type 19480b57cec5SDimitry Andric__move_backward(_Tp* __first, _Tp* __last, _Up* __result) 19490b57cec5SDimitry Andric{ 1950*e8d8bef9SDimitry Andric if (__libcpp_is_constant_evaluated()) 1951*e8d8bef9SDimitry Andric return _VSTD::__move_backward_constexpr(__first, __last, __result); 19520b57cec5SDimitry Andric const size_t __n = static_cast<size_t>(__last - __first); 19530b57cec5SDimitry Andric if (__n > 0) 19540b57cec5SDimitry Andric { 19550b57cec5SDimitry Andric __result -= __n; 19560b57cec5SDimitry Andric _VSTD::memmove(__result, __first, __n * sizeof(_Up)); 19570b57cec5SDimitry Andric } 19580b57cec5SDimitry Andric return __result; 19590b57cec5SDimitry Andric} 19600b57cec5SDimitry Andric 19610b57cec5SDimitry Andrictemplate <class _BidirectionalIterator1, class _BidirectionalIterator2> 1962*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 19630b57cec5SDimitry Andric_BidirectionalIterator2 19640b57cec5SDimitry Andricmove_backward(_BidirectionalIterator1 __first, _BidirectionalIterator1 __last, 19650b57cec5SDimitry Andric _BidirectionalIterator2 __result) 19660b57cec5SDimitry Andric{ 1967*e8d8bef9SDimitry Andric return _VSTD::__move_backward(_VSTD::__unwrap_iter(__first), _VSTD::__unwrap_iter(__last), _VSTD::__unwrap_iter(__result)); 19680b57cec5SDimitry Andric} 19690b57cec5SDimitry Andric 19700b57cec5SDimitry Andric// iter_swap 19710b57cec5SDimitry Andric 19720b57cec5SDimitry Andric// moved to <type_traits> for better swap / noexcept support 19730b57cec5SDimitry Andric 19740b57cec5SDimitry Andric// transform 19750b57cec5SDimitry Andric 19760b57cec5SDimitry Andrictemplate <class _InputIterator, class _OutputIterator, class _UnaryOperation> 19770b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 19780b57cec5SDimitry Andric_OutputIterator 19790b57cec5SDimitry Andrictransform(_InputIterator __first, _InputIterator __last, _OutputIterator __result, _UnaryOperation __op) 19800b57cec5SDimitry Andric{ 19810b57cec5SDimitry Andric for (; __first != __last; ++__first, (void) ++__result) 19820b57cec5SDimitry Andric *__result = __op(*__first); 19830b57cec5SDimitry Andric return __result; 19840b57cec5SDimitry Andric} 19850b57cec5SDimitry Andric 19860b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _OutputIterator, class _BinaryOperation> 19870b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 19880b57cec5SDimitry Andric_OutputIterator 19890b57cec5SDimitry Andrictransform(_InputIterator1 __first1, _InputIterator1 __last1, _InputIterator2 __first2, 19900b57cec5SDimitry Andric _OutputIterator __result, _BinaryOperation __binary_op) 19910b57cec5SDimitry Andric{ 19920b57cec5SDimitry Andric for (; __first1 != __last1; ++__first1, (void) ++__first2, ++__result) 19930b57cec5SDimitry Andric *__result = __binary_op(*__first1, *__first2); 19940b57cec5SDimitry Andric return __result; 19950b57cec5SDimitry Andric} 19960b57cec5SDimitry Andric 19970b57cec5SDimitry Andric// replace 19980b57cec5SDimitry Andric 19990b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Tp> 20000b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 20010b57cec5SDimitry Andricvoid 20020b57cec5SDimitry Andricreplace(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __old_value, const _Tp& __new_value) 20030b57cec5SDimitry Andric{ 20040b57cec5SDimitry Andric for (; __first != __last; ++__first) 20050b57cec5SDimitry Andric if (*__first == __old_value) 20060b57cec5SDimitry Andric *__first = __new_value; 20070b57cec5SDimitry Andric} 20080b57cec5SDimitry Andric 20090b57cec5SDimitry Andric// replace_if 20100b57cec5SDimitry Andric 20110b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Predicate, class _Tp> 20120b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 20130b57cec5SDimitry Andricvoid 20140b57cec5SDimitry Andricreplace_if(_ForwardIterator __first, _ForwardIterator __last, _Predicate __pred, const _Tp& __new_value) 20150b57cec5SDimitry Andric{ 20160b57cec5SDimitry Andric for (; __first != __last; ++__first) 20170b57cec5SDimitry Andric if (__pred(*__first)) 20180b57cec5SDimitry Andric *__first = __new_value; 20190b57cec5SDimitry Andric} 20200b57cec5SDimitry Andric 20210b57cec5SDimitry Andric// replace_copy 20220b57cec5SDimitry Andric 20230b57cec5SDimitry Andrictemplate <class _InputIterator, class _OutputIterator, class _Tp> 20240b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 20250b57cec5SDimitry Andric_OutputIterator 20260b57cec5SDimitry Andricreplace_copy(_InputIterator __first, _InputIterator __last, _OutputIterator __result, 20270b57cec5SDimitry Andric const _Tp& __old_value, const _Tp& __new_value) 20280b57cec5SDimitry Andric{ 20290b57cec5SDimitry Andric for (; __first != __last; ++__first, (void) ++__result) 20300b57cec5SDimitry Andric if (*__first == __old_value) 20310b57cec5SDimitry Andric *__result = __new_value; 20320b57cec5SDimitry Andric else 20330b57cec5SDimitry Andric *__result = *__first; 20340b57cec5SDimitry Andric return __result; 20350b57cec5SDimitry Andric} 20360b57cec5SDimitry Andric 20370b57cec5SDimitry Andric// replace_copy_if 20380b57cec5SDimitry Andric 20390b57cec5SDimitry Andrictemplate <class _InputIterator, class _OutputIterator, class _Predicate, class _Tp> 20400b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 20410b57cec5SDimitry Andric_OutputIterator 20420b57cec5SDimitry Andricreplace_copy_if(_InputIterator __first, _InputIterator __last, _OutputIterator __result, 20430b57cec5SDimitry Andric _Predicate __pred, const _Tp& __new_value) 20440b57cec5SDimitry Andric{ 20450b57cec5SDimitry Andric for (; __first != __last; ++__first, (void) ++__result) 20460b57cec5SDimitry Andric if (__pred(*__first)) 20470b57cec5SDimitry Andric *__result = __new_value; 20480b57cec5SDimitry Andric else 20490b57cec5SDimitry Andric *__result = *__first; 20500b57cec5SDimitry Andric return __result; 20510b57cec5SDimitry Andric} 20520b57cec5SDimitry Andric 20530b57cec5SDimitry Andric// fill_n 20540b57cec5SDimitry Andric 20550b57cec5SDimitry Andrictemplate <class _OutputIterator, class _Size, class _Tp> 20560b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 20570b57cec5SDimitry Andric_OutputIterator 20580b57cec5SDimitry Andric__fill_n(_OutputIterator __first, _Size __n, const _Tp& __value_) 20590b57cec5SDimitry Andric{ 20600b57cec5SDimitry Andric for (; __n > 0; ++__first, (void) --__n) 20610b57cec5SDimitry Andric *__first = __value_; 20620b57cec5SDimitry Andric return __first; 20630b57cec5SDimitry Andric} 20640b57cec5SDimitry Andric 20650b57cec5SDimitry Andrictemplate <class _OutputIterator, class _Size, class _Tp> 20660b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 20670b57cec5SDimitry Andric_OutputIterator 20680b57cec5SDimitry Andricfill_n(_OutputIterator __first, _Size __n, const _Tp& __value_) 20690b57cec5SDimitry Andric{ 2070*e8d8bef9SDimitry Andric return _VSTD::__fill_n(__first, _VSTD::__convert_to_integral(__n), __value_); 20710b57cec5SDimitry Andric} 20720b57cec5SDimitry Andric 20730b57cec5SDimitry Andric// fill 20740b57cec5SDimitry Andric 20750b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Tp> 20760b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 20770b57cec5SDimitry Andricvoid 20780b57cec5SDimitry Andric__fill(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_, forward_iterator_tag) 20790b57cec5SDimitry Andric{ 20800b57cec5SDimitry Andric for (; __first != __last; ++__first) 20810b57cec5SDimitry Andric *__first = __value_; 20820b57cec5SDimitry Andric} 20830b57cec5SDimitry Andric 20840b57cec5SDimitry Andrictemplate <class _RandomAccessIterator, class _Tp> 20850b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 20860b57cec5SDimitry Andricvoid 20870b57cec5SDimitry Andric__fill(_RandomAccessIterator __first, _RandomAccessIterator __last, const _Tp& __value_, random_access_iterator_tag) 20880b57cec5SDimitry Andric{ 20890b57cec5SDimitry Andric _VSTD::fill_n(__first, __last - __first, __value_); 20900b57cec5SDimitry Andric} 20910b57cec5SDimitry Andric 20920b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Tp> 20930b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 20940b57cec5SDimitry Andricvoid 20950b57cec5SDimitry Andricfill(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_) 20960b57cec5SDimitry Andric{ 20970b57cec5SDimitry Andric _VSTD::__fill(__first, __last, __value_, typename iterator_traits<_ForwardIterator>::iterator_category()); 20980b57cec5SDimitry Andric} 20990b57cec5SDimitry Andric 21000b57cec5SDimitry Andric// generate 21010b57cec5SDimitry Andric 21020b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Generator> 21030b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 21040b57cec5SDimitry Andricvoid 21050b57cec5SDimitry Andricgenerate(_ForwardIterator __first, _ForwardIterator __last, _Generator __gen) 21060b57cec5SDimitry Andric{ 21070b57cec5SDimitry Andric for (; __first != __last; ++__first) 21080b57cec5SDimitry Andric *__first = __gen(); 21090b57cec5SDimitry Andric} 21100b57cec5SDimitry Andric 21110b57cec5SDimitry Andric// generate_n 21120b57cec5SDimitry Andric 21130b57cec5SDimitry Andrictemplate <class _OutputIterator, class _Size, class _Generator> 21140b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 21150b57cec5SDimitry Andric_OutputIterator 21160b57cec5SDimitry Andricgenerate_n(_OutputIterator __first, _Size __orig_n, _Generator __gen) 21170b57cec5SDimitry Andric{ 2118*e8d8bef9SDimitry Andric typedef decltype(_VSTD::__convert_to_integral(__orig_n)) _IntegralSize; 21190b57cec5SDimitry Andric _IntegralSize __n = __orig_n; 21200b57cec5SDimitry Andric for (; __n > 0; ++__first, (void) --__n) 21210b57cec5SDimitry Andric *__first = __gen(); 21220b57cec5SDimitry Andric return __first; 21230b57cec5SDimitry Andric} 21240b57cec5SDimitry Andric 21250b57cec5SDimitry Andric// remove 21260b57cec5SDimitry Andric 21270b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Tp> 21280b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT _LIBCPP_CONSTEXPR_AFTER_CXX17 _ForwardIterator 21290b57cec5SDimitry Andricremove(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_) 21300b57cec5SDimitry Andric{ 21310b57cec5SDimitry Andric __first = _VSTD::find(__first, __last, __value_); 21320b57cec5SDimitry Andric if (__first != __last) 21330b57cec5SDimitry Andric { 21340b57cec5SDimitry Andric _ForwardIterator __i = __first; 21350b57cec5SDimitry Andric while (++__i != __last) 21360b57cec5SDimitry Andric { 21370b57cec5SDimitry Andric if (!(*__i == __value_)) 21380b57cec5SDimitry Andric { 21390b57cec5SDimitry Andric *__first = _VSTD::move(*__i); 21400b57cec5SDimitry Andric ++__first; 21410b57cec5SDimitry Andric } 21420b57cec5SDimitry Andric } 21430b57cec5SDimitry Andric } 21440b57cec5SDimitry Andric return __first; 21450b57cec5SDimitry Andric} 21460b57cec5SDimitry Andric 21470b57cec5SDimitry Andric// remove_if 21480b57cec5SDimitry Andric 21490b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Predicate> 21500b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT _LIBCPP_CONSTEXPR_AFTER_CXX17 _ForwardIterator 21510b57cec5SDimitry Andricremove_if(_ForwardIterator __first, _ForwardIterator __last, _Predicate __pred) 21520b57cec5SDimitry Andric{ 21530b57cec5SDimitry Andric __first = _VSTD::find_if<_ForwardIterator, typename add_lvalue_reference<_Predicate>::type> 21540b57cec5SDimitry Andric (__first, __last, __pred); 21550b57cec5SDimitry Andric if (__first != __last) 21560b57cec5SDimitry Andric { 21570b57cec5SDimitry Andric _ForwardIterator __i = __first; 21580b57cec5SDimitry Andric while (++__i != __last) 21590b57cec5SDimitry Andric { 21600b57cec5SDimitry Andric if (!__pred(*__i)) 21610b57cec5SDimitry Andric { 21620b57cec5SDimitry Andric *__first = _VSTD::move(*__i); 21630b57cec5SDimitry Andric ++__first; 21640b57cec5SDimitry Andric } 21650b57cec5SDimitry Andric } 21660b57cec5SDimitry Andric } 21670b57cec5SDimitry Andric return __first; 21680b57cec5SDimitry Andric} 21690b57cec5SDimitry Andric 21700b57cec5SDimitry Andric// remove_copy 21710b57cec5SDimitry Andric 21720b57cec5SDimitry Andrictemplate <class _InputIterator, class _OutputIterator, class _Tp> 21730b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 21740b57cec5SDimitry Andric_OutputIterator 21750b57cec5SDimitry Andricremove_copy(_InputIterator __first, _InputIterator __last, _OutputIterator __result, const _Tp& __value_) 21760b57cec5SDimitry Andric{ 21770b57cec5SDimitry Andric for (; __first != __last; ++__first) 21780b57cec5SDimitry Andric { 21790b57cec5SDimitry Andric if (!(*__first == __value_)) 21800b57cec5SDimitry Andric { 21810b57cec5SDimitry Andric *__result = *__first; 21820b57cec5SDimitry Andric ++__result; 21830b57cec5SDimitry Andric } 21840b57cec5SDimitry Andric } 21850b57cec5SDimitry Andric return __result; 21860b57cec5SDimitry Andric} 21870b57cec5SDimitry Andric 21880b57cec5SDimitry Andric// remove_copy_if 21890b57cec5SDimitry Andric 21900b57cec5SDimitry Andrictemplate <class _InputIterator, class _OutputIterator, class _Predicate> 21910b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 21920b57cec5SDimitry Andric_OutputIterator 21930b57cec5SDimitry Andricremove_copy_if(_InputIterator __first, _InputIterator __last, _OutputIterator __result, _Predicate __pred) 21940b57cec5SDimitry Andric{ 21950b57cec5SDimitry Andric for (; __first != __last; ++__first) 21960b57cec5SDimitry Andric { 21970b57cec5SDimitry Andric if (!__pred(*__first)) 21980b57cec5SDimitry Andric { 21990b57cec5SDimitry Andric *__result = *__first; 22000b57cec5SDimitry Andric ++__result; 22010b57cec5SDimitry Andric } 22020b57cec5SDimitry Andric } 22030b57cec5SDimitry Andric return __result; 22040b57cec5SDimitry Andric} 22050b57cec5SDimitry Andric 22060b57cec5SDimitry Andric// unique 22070b57cec5SDimitry Andric 22080b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _BinaryPredicate> 22090b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT _LIBCPP_CONSTEXPR_AFTER_CXX17 _ForwardIterator 22100b57cec5SDimitry Andricunique(_ForwardIterator __first, _ForwardIterator __last, _BinaryPredicate __pred) 22110b57cec5SDimitry Andric{ 22120b57cec5SDimitry Andric __first = _VSTD::adjacent_find<_ForwardIterator, typename add_lvalue_reference<_BinaryPredicate>::type> 22130b57cec5SDimitry Andric (__first, __last, __pred); 22140b57cec5SDimitry Andric if (__first != __last) 22150b57cec5SDimitry Andric { 22160b57cec5SDimitry Andric // ... a a ? ... 22170b57cec5SDimitry Andric // f i 22180b57cec5SDimitry Andric _ForwardIterator __i = __first; 22190b57cec5SDimitry Andric for (++__i; ++__i != __last;) 22200b57cec5SDimitry Andric if (!__pred(*__first, *__i)) 22210b57cec5SDimitry Andric *++__first = _VSTD::move(*__i); 22220b57cec5SDimitry Andric ++__first; 22230b57cec5SDimitry Andric } 22240b57cec5SDimitry Andric return __first; 22250b57cec5SDimitry Andric} 22260b57cec5SDimitry Andric 22270b57cec5SDimitry Andrictemplate <class _ForwardIterator> 22280b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 22290b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 22300b57cec5SDimitry Andric_ForwardIterator 22310b57cec5SDimitry Andricunique(_ForwardIterator __first, _ForwardIterator __last) 22320b57cec5SDimitry Andric{ 22330b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator>::value_type __v; 22340b57cec5SDimitry Andric return _VSTD::unique(__first, __last, __equal_to<__v>()); 22350b57cec5SDimitry Andric} 22360b57cec5SDimitry Andric 22370b57cec5SDimitry Andric// unique_copy 22380b57cec5SDimitry Andric 22390b57cec5SDimitry Andrictemplate <class _BinaryPredicate, class _InputIterator, class _OutputIterator> 22400b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _OutputIterator 22410b57cec5SDimitry Andric__unique_copy(_InputIterator __first, _InputIterator __last, _OutputIterator __result, _BinaryPredicate __pred, 22420b57cec5SDimitry Andric input_iterator_tag, output_iterator_tag) 22430b57cec5SDimitry Andric{ 22440b57cec5SDimitry Andric if (__first != __last) 22450b57cec5SDimitry Andric { 22460b57cec5SDimitry Andric typename iterator_traits<_InputIterator>::value_type __t(*__first); 22470b57cec5SDimitry Andric *__result = __t; 22480b57cec5SDimitry Andric ++__result; 22490b57cec5SDimitry Andric while (++__first != __last) 22500b57cec5SDimitry Andric { 22510b57cec5SDimitry Andric if (!__pred(__t, *__first)) 22520b57cec5SDimitry Andric { 22530b57cec5SDimitry Andric __t = *__first; 22540b57cec5SDimitry Andric *__result = __t; 22550b57cec5SDimitry Andric ++__result; 22560b57cec5SDimitry Andric } 22570b57cec5SDimitry Andric } 22580b57cec5SDimitry Andric } 22590b57cec5SDimitry Andric return __result; 22600b57cec5SDimitry Andric} 22610b57cec5SDimitry Andric 22620b57cec5SDimitry Andrictemplate <class _BinaryPredicate, class _ForwardIterator, class _OutputIterator> 22630b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _OutputIterator 22640b57cec5SDimitry Andric__unique_copy(_ForwardIterator __first, _ForwardIterator __last, _OutputIterator __result, _BinaryPredicate __pred, 22650b57cec5SDimitry Andric forward_iterator_tag, output_iterator_tag) 22660b57cec5SDimitry Andric{ 22670b57cec5SDimitry Andric if (__first != __last) 22680b57cec5SDimitry Andric { 22690b57cec5SDimitry Andric _ForwardIterator __i = __first; 22700b57cec5SDimitry Andric *__result = *__i; 22710b57cec5SDimitry Andric ++__result; 22720b57cec5SDimitry Andric while (++__first != __last) 22730b57cec5SDimitry Andric { 22740b57cec5SDimitry Andric if (!__pred(*__i, *__first)) 22750b57cec5SDimitry Andric { 22760b57cec5SDimitry Andric *__result = *__first; 22770b57cec5SDimitry Andric ++__result; 22780b57cec5SDimitry Andric __i = __first; 22790b57cec5SDimitry Andric } 22800b57cec5SDimitry Andric } 22810b57cec5SDimitry Andric } 22820b57cec5SDimitry Andric return __result; 22830b57cec5SDimitry Andric} 22840b57cec5SDimitry Andric 22850b57cec5SDimitry Andrictemplate <class _BinaryPredicate, class _InputIterator, class _ForwardIterator> 22860b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _ForwardIterator 22870b57cec5SDimitry Andric__unique_copy(_InputIterator __first, _InputIterator __last, _ForwardIterator __result, _BinaryPredicate __pred, 22880b57cec5SDimitry Andric input_iterator_tag, forward_iterator_tag) 22890b57cec5SDimitry Andric{ 22900b57cec5SDimitry Andric if (__first != __last) 22910b57cec5SDimitry Andric { 22920b57cec5SDimitry Andric *__result = *__first; 22930b57cec5SDimitry Andric while (++__first != __last) 22940b57cec5SDimitry Andric if (!__pred(*__result, *__first)) 22950b57cec5SDimitry Andric *++__result = *__first; 22960b57cec5SDimitry Andric ++__result; 22970b57cec5SDimitry Andric } 22980b57cec5SDimitry Andric return __result; 22990b57cec5SDimitry Andric} 23000b57cec5SDimitry Andric 23010b57cec5SDimitry Andrictemplate <class _InputIterator, class _OutputIterator, class _BinaryPredicate> 23020b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 23030b57cec5SDimitry Andric_OutputIterator 23040b57cec5SDimitry Andricunique_copy(_InputIterator __first, _InputIterator __last, _OutputIterator __result, _BinaryPredicate __pred) 23050b57cec5SDimitry Andric{ 23060b57cec5SDimitry Andric return _VSTD::__unique_copy<typename add_lvalue_reference<_BinaryPredicate>::type> 23070b57cec5SDimitry Andric (__first, __last, __result, __pred, 23080b57cec5SDimitry Andric typename iterator_traits<_InputIterator>::iterator_category(), 23090b57cec5SDimitry Andric typename iterator_traits<_OutputIterator>::iterator_category()); 23100b57cec5SDimitry Andric} 23110b57cec5SDimitry Andric 23120b57cec5SDimitry Andrictemplate <class _InputIterator, class _OutputIterator> 23130b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 23140b57cec5SDimitry Andric_OutputIterator 23150b57cec5SDimitry Andricunique_copy(_InputIterator __first, _InputIterator __last, _OutputIterator __result) 23160b57cec5SDimitry Andric{ 23170b57cec5SDimitry Andric typedef typename iterator_traits<_InputIterator>::value_type __v; 23180b57cec5SDimitry Andric return _VSTD::unique_copy(__first, __last, __result, __equal_to<__v>()); 23190b57cec5SDimitry Andric} 23200b57cec5SDimitry Andric 23210b57cec5SDimitry Andric// reverse 23220b57cec5SDimitry Andric 23230b57cec5SDimitry Andrictemplate <class _BidirectionalIterator> 2324*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 23250b57cec5SDimitry Andricvoid 23260b57cec5SDimitry Andric__reverse(_BidirectionalIterator __first, _BidirectionalIterator __last, bidirectional_iterator_tag) 23270b57cec5SDimitry Andric{ 23280b57cec5SDimitry Andric while (__first != __last) 23290b57cec5SDimitry Andric { 23300b57cec5SDimitry Andric if (__first == --__last) 23310b57cec5SDimitry Andric break; 23320b57cec5SDimitry Andric _VSTD::iter_swap(__first, __last); 23330b57cec5SDimitry Andric ++__first; 23340b57cec5SDimitry Andric } 23350b57cec5SDimitry Andric} 23360b57cec5SDimitry Andric 23370b57cec5SDimitry Andrictemplate <class _RandomAccessIterator> 2338*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 23390b57cec5SDimitry Andricvoid 23400b57cec5SDimitry Andric__reverse(_RandomAccessIterator __first, _RandomAccessIterator __last, random_access_iterator_tag) 23410b57cec5SDimitry Andric{ 23420b57cec5SDimitry Andric if (__first != __last) 23430b57cec5SDimitry Andric for (; __first < --__last; ++__first) 23440b57cec5SDimitry Andric _VSTD::iter_swap(__first, __last); 23450b57cec5SDimitry Andric} 23460b57cec5SDimitry Andric 23470b57cec5SDimitry Andrictemplate <class _BidirectionalIterator> 2348*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 23490b57cec5SDimitry Andricvoid 23500b57cec5SDimitry Andricreverse(_BidirectionalIterator __first, _BidirectionalIterator __last) 23510b57cec5SDimitry Andric{ 23520b57cec5SDimitry Andric _VSTD::__reverse(__first, __last, typename iterator_traits<_BidirectionalIterator>::iterator_category()); 23530b57cec5SDimitry Andric} 23540b57cec5SDimitry Andric 23550b57cec5SDimitry Andric// reverse_copy 23560b57cec5SDimitry Andric 23570b57cec5SDimitry Andrictemplate <class _BidirectionalIterator, class _OutputIterator> 23580b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 23590b57cec5SDimitry Andric_OutputIterator 23600b57cec5SDimitry Andricreverse_copy(_BidirectionalIterator __first, _BidirectionalIterator __last, _OutputIterator __result) 23610b57cec5SDimitry Andric{ 23620b57cec5SDimitry Andric for (; __first != __last; ++__result) 23630b57cec5SDimitry Andric *__result = *--__last; 23640b57cec5SDimitry Andric return __result; 23650b57cec5SDimitry Andric} 23660b57cec5SDimitry Andric 23670b57cec5SDimitry Andric// rotate 23680b57cec5SDimitry Andric 23690b57cec5SDimitry Andrictemplate <class _ForwardIterator> 2370*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX11 _ForwardIterator 23710b57cec5SDimitry Andric__rotate_left(_ForwardIterator __first, _ForwardIterator __last) 23720b57cec5SDimitry Andric{ 23730b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator>::value_type value_type; 23740b57cec5SDimitry Andric value_type __tmp = _VSTD::move(*__first); 23750b57cec5SDimitry Andric _ForwardIterator __lm1 = _VSTD::move(_VSTD::next(__first), __last, __first); 23760b57cec5SDimitry Andric *__lm1 = _VSTD::move(__tmp); 23770b57cec5SDimitry Andric return __lm1; 23780b57cec5SDimitry Andric} 23790b57cec5SDimitry Andric 23800b57cec5SDimitry Andrictemplate <class _BidirectionalIterator> 2381*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX11 _BidirectionalIterator 23820b57cec5SDimitry Andric__rotate_right(_BidirectionalIterator __first, _BidirectionalIterator __last) 23830b57cec5SDimitry Andric{ 23840b57cec5SDimitry Andric typedef typename iterator_traits<_BidirectionalIterator>::value_type value_type; 23850b57cec5SDimitry Andric _BidirectionalIterator __lm1 = _VSTD::prev(__last); 23860b57cec5SDimitry Andric value_type __tmp = _VSTD::move(*__lm1); 23870b57cec5SDimitry Andric _BidirectionalIterator __fp1 = _VSTD::move_backward(__first, __lm1, __last); 23880b57cec5SDimitry Andric *__first = _VSTD::move(__tmp); 23890b57cec5SDimitry Andric return __fp1; 23900b57cec5SDimitry Andric} 23910b57cec5SDimitry Andric 23920b57cec5SDimitry Andrictemplate <class _ForwardIterator> 2393*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX14 _ForwardIterator 23940b57cec5SDimitry Andric__rotate_forward(_ForwardIterator __first, _ForwardIterator __middle, _ForwardIterator __last) 23950b57cec5SDimitry Andric{ 23960b57cec5SDimitry Andric _ForwardIterator __i = __middle; 23970b57cec5SDimitry Andric while (true) 23980b57cec5SDimitry Andric { 23990b57cec5SDimitry Andric swap(*__first, *__i); 24000b57cec5SDimitry Andric ++__first; 24010b57cec5SDimitry Andric if (++__i == __last) 24020b57cec5SDimitry Andric break; 24030b57cec5SDimitry Andric if (__first == __middle) 24040b57cec5SDimitry Andric __middle = __i; 24050b57cec5SDimitry Andric } 24060b57cec5SDimitry Andric _ForwardIterator __r = __first; 24070b57cec5SDimitry Andric if (__first != __middle) 24080b57cec5SDimitry Andric { 24090b57cec5SDimitry Andric __i = __middle; 24100b57cec5SDimitry Andric while (true) 24110b57cec5SDimitry Andric { 24120b57cec5SDimitry Andric swap(*__first, *__i); 24130b57cec5SDimitry Andric ++__first; 24140b57cec5SDimitry Andric if (++__i == __last) 24150b57cec5SDimitry Andric { 24160b57cec5SDimitry Andric if (__first == __middle) 24170b57cec5SDimitry Andric break; 24180b57cec5SDimitry Andric __i = __middle; 24190b57cec5SDimitry Andric } 24200b57cec5SDimitry Andric else if (__first == __middle) 24210b57cec5SDimitry Andric __middle = __i; 24220b57cec5SDimitry Andric } 24230b57cec5SDimitry Andric } 24240b57cec5SDimitry Andric return __r; 24250b57cec5SDimitry Andric} 24260b57cec5SDimitry Andric 24270b57cec5SDimitry Andrictemplate<typename _Integral> 24280b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 2429*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX14 _Integral 24300b57cec5SDimitry Andric__algo_gcd(_Integral __x, _Integral __y) 24310b57cec5SDimitry Andric{ 24320b57cec5SDimitry Andric do 24330b57cec5SDimitry Andric { 24340b57cec5SDimitry Andric _Integral __t = __x % __y; 24350b57cec5SDimitry Andric __x = __y; 24360b57cec5SDimitry Andric __y = __t; 24370b57cec5SDimitry Andric } while (__y); 24380b57cec5SDimitry Andric return __x; 24390b57cec5SDimitry Andric} 24400b57cec5SDimitry Andric 24410b57cec5SDimitry Andrictemplate<typename _RandomAccessIterator> 2442*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX14 _RandomAccessIterator 24430b57cec5SDimitry Andric__rotate_gcd(_RandomAccessIterator __first, _RandomAccessIterator __middle, _RandomAccessIterator __last) 24440b57cec5SDimitry Andric{ 24450b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::difference_type difference_type; 24460b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::value_type value_type; 24470b57cec5SDimitry Andric 24480b57cec5SDimitry Andric const difference_type __m1 = __middle - __first; 24490b57cec5SDimitry Andric const difference_type __m2 = __last - __middle; 24500b57cec5SDimitry Andric if (__m1 == __m2) 24510b57cec5SDimitry Andric { 24520b57cec5SDimitry Andric _VSTD::swap_ranges(__first, __middle, __middle); 24530b57cec5SDimitry Andric return __middle; 24540b57cec5SDimitry Andric } 24550b57cec5SDimitry Andric const difference_type __g = _VSTD::__algo_gcd(__m1, __m2); 24560b57cec5SDimitry Andric for (_RandomAccessIterator __p = __first + __g; __p != __first;) 24570b57cec5SDimitry Andric { 24580b57cec5SDimitry Andric value_type __t(_VSTD::move(*--__p)); 24590b57cec5SDimitry Andric _RandomAccessIterator __p1 = __p; 24600b57cec5SDimitry Andric _RandomAccessIterator __p2 = __p1 + __m1; 24610b57cec5SDimitry Andric do 24620b57cec5SDimitry Andric { 24630b57cec5SDimitry Andric *__p1 = _VSTD::move(*__p2); 24640b57cec5SDimitry Andric __p1 = __p2; 24650b57cec5SDimitry Andric const difference_type __d = __last - __p2; 24660b57cec5SDimitry Andric if (__m1 < __d) 24670b57cec5SDimitry Andric __p2 += __m1; 24680b57cec5SDimitry Andric else 24690b57cec5SDimitry Andric __p2 = __first + (__m1 - __d); 24700b57cec5SDimitry Andric } while (__p2 != __p); 24710b57cec5SDimitry Andric *__p1 = _VSTD::move(__t); 24720b57cec5SDimitry Andric } 24730b57cec5SDimitry Andric return __first + __m2; 24740b57cec5SDimitry Andric} 24750b57cec5SDimitry Andric 24760b57cec5SDimitry Andrictemplate <class _ForwardIterator> 24770b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 2478*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX11 _ForwardIterator 24790b57cec5SDimitry Andric__rotate(_ForwardIterator __first, _ForwardIterator __middle, _ForwardIterator __last, 24800b57cec5SDimitry Andric _VSTD::forward_iterator_tag) 24810b57cec5SDimitry Andric{ 24820b57cec5SDimitry Andric typedef typename _VSTD::iterator_traits<_ForwardIterator>::value_type value_type; 24830b57cec5SDimitry Andric if (_VSTD::is_trivially_move_assignable<value_type>::value) 24840b57cec5SDimitry Andric { 24850b57cec5SDimitry Andric if (_VSTD::next(__first) == __middle) 24860b57cec5SDimitry Andric return _VSTD::__rotate_left(__first, __last); 24870b57cec5SDimitry Andric } 24880b57cec5SDimitry Andric return _VSTD::__rotate_forward(__first, __middle, __last); 24890b57cec5SDimitry Andric} 24900b57cec5SDimitry Andric 24910b57cec5SDimitry Andrictemplate <class _BidirectionalIterator> 24920b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 2493*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX11 _BidirectionalIterator 24940b57cec5SDimitry Andric__rotate(_BidirectionalIterator __first, _BidirectionalIterator __middle, _BidirectionalIterator __last, 24950b57cec5SDimitry Andric _VSTD::bidirectional_iterator_tag) 24960b57cec5SDimitry Andric{ 24970b57cec5SDimitry Andric typedef typename _VSTD::iterator_traits<_BidirectionalIterator>::value_type value_type; 24980b57cec5SDimitry Andric if (_VSTD::is_trivially_move_assignable<value_type>::value) 24990b57cec5SDimitry Andric { 25000b57cec5SDimitry Andric if (_VSTD::next(__first) == __middle) 25010b57cec5SDimitry Andric return _VSTD::__rotate_left(__first, __last); 25020b57cec5SDimitry Andric if (_VSTD::next(__middle) == __last) 25030b57cec5SDimitry Andric return _VSTD::__rotate_right(__first, __last); 25040b57cec5SDimitry Andric } 25050b57cec5SDimitry Andric return _VSTD::__rotate_forward(__first, __middle, __last); 25060b57cec5SDimitry Andric} 25070b57cec5SDimitry Andric 25080b57cec5SDimitry Andrictemplate <class _RandomAccessIterator> 25090b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 2510*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX11 _RandomAccessIterator 25110b57cec5SDimitry Andric__rotate(_RandomAccessIterator __first, _RandomAccessIterator __middle, _RandomAccessIterator __last, 25120b57cec5SDimitry Andric _VSTD::random_access_iterator_tag) 25130b57cec5SDimitry Andric{ 25140b57cec5SDimitry Andric typedef typename _VSTD::iterator_traits<_RandomAccessIterator>::value_type value_type; 25150b57cec5SDimitry Andric if (_VSTD::is_trivially_move_assignable<value_type>::value) 25160b57cec5SDimitry Andric { 25170b57cec5SDimitry Andric if (_VSTD::next(__first) == __middle) 25180b57cec5SDimitry Andric return _VSTD::__rotate_left(__first, __last); 25190b57cec5SDimitry Andric if (_VSTD::next(__middle) == __last) 25200b57cec5SDimitry Andric return _VSTD::__rotate_right(__first, __last); 25210b57cec5SDimitry Andric return _VSTD::__rotate_gcd(__first, __middle, __last); 25220b57cec5SDimitry Andric } 25230b57cec5SDimitry Andric return _VSTD::__rotate_forward(__first, __middle, __last); 25240b57cec5SDimitry Andric} 25250b57cec5SDimitry Andric 25260b57cec5SDimitry Andrictemplate <class _ForwardIterator> 25270b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 2528*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _ForwardIterator 25290b57cec5SDimitry Andricrotate(_ForwardIterator __first, _ForwardIterator __middle, _ForwardIterator __last) 25300b57cec5SDimitry Andric{ 25310b57cec5SDimitry Andric if (__first == __middle) 25320b57cec5SDimitry Andric return __last; 25330b57cec5SDimitry Andric if (__middle == __last) 25340b57cec5SDimitry Andric return __first; 25350b57cec5SDimitry Andric return _VSTD::__rotate(__first, __middle, __last, 25360b57cec5SDimitry Andric typename _VSTD::iterator_traits<_ForwardIterator>::iterator_category()); 25370b57cec5SDimitry Andric} 25380b57cec5SDimitry Andric 25390b57cec5SDimitry Andric// rotate_copy 25400b57cec5SDimitry Andric 25410b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _OutputIterator> 2542*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 25430b57cec5SDimitry Andric_OutputIterator 25440b57cec5SDimitry Andricrotate_copy(_ForwardIterator __first, _ForwardIterator __middle, _ForwardIterator __last, _OutputIterator __result) 25450b57cec5SDimitry Andric{ 25460b57cec5SDimitry Andric return _VSTD::copy(__first, __middle, _VSTD::copy(__middle, __last, __result)); 25470b57cec5SDimitry Andric} 25480b57cec5SDimitry Andric 25490b57cec5SDimitry Andric// min_element 25500b57cec5SDimitry Andric 25510b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Compare> 25520b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 25530b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 25540b57cec5SDimitry Andric_ForwardIterator 25550b57cec5SDimitry Andricmin_element(_ForwardIterator __first, _ForwardIterator __last, _Compare __comp) 25560b57cec5SDimitry Andric{ 2557480093f4SDimitry Andric static_assert(__is_cpp17_forward_iterator<_ForwardIterator>::value, 25580b57cec5SDimitry Andric "std::min_element requires a ForwardIterator"); 25590b57cec5SDimitry Andric if (__first != __last) 25600b57cec5SDimitry Andric { 25610b57cec5SDimitry Andric _ForwardIterator __i = __first; 25620b57cec5SDimitry Andric while (++__i != __last) 25630b57cec5SDimitry Andric if (__comp(*__i, *__first)) 25640b57cec5SDimitry Andric __first = __i; 25650b57cec5SDimitry Andric } 25660b57cec5SDimitry Andric return __first; 25670b57cec5SDimitry Andric} 25680b57cec5SDimitry Andric 25690b57cec5SDimitry Andrictemplate <class _ForwardIterator> 25700b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 25710b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 25720b57cec5SDimitry Andric_ForwardIterator 25730b57cec5SDimitry Andricmin_element(_ForwardIterator __first, _ForwardIterator __last) 25740b57cec5SDimitry Andric{ 25750b57cec5SDimitry Andric return _VSTD::min_element(__first, __last, 25760b57cec5SDimitry Andric __less<typename iterator_traits<_ForwardIterator>::value_type>()); 25770b57cec5SDimitry Andric} 25780b57cec5SDimitry Andric 25790b57cec5SDimitry Andric// min 25800b57cec5SDimitry Andric 25810b57cec5SDimitry Andrictemplate <class _Tp, class _Compare> 25820b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 25830b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 25840b57cec5SDimitry Andricconst _Tp& 25850b57cec5SDimitry Andricmin(const _Tp& __a, const _Tp& __b, _Compare __comp) 25860b57cec5SDimitry Andric{ 25870b57cec5SDimitry Andric return __comp(__b, __a) ? __b : __a; 25880b57cec5SDimitry Andric} 25890b57cec5SDimitry Andric 25900b57cec5SDimitry Andrictemplate <class _Tp> 25910b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 25920b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 25930b57cec5SDimitry Andricconst _Tp& 25940b57cec5SDimitry Andricmin(const _Tp& __a, const _Tp& __b) 25950b57cec5SDimitry Andric{ 25960b57cec5SDimitry Andric return _VSTD::min(__a, __b, __less<_Tp>()); 25970b57cec5SDimitry Andric} 25980b57cec5SDimitry Andric 25990b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG 26000b57cec5SDimitry Andric 26010b57cec5SDimitry Andrictemplate<class _Tp, class _Compare> 26020b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 26030b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 26040b57cec5SDimitry Andric_Tp 26050b57cec5SDimitry Andricmin(initializer_list<_Tp> __t, _Compare __comp) 26060b57cec5SDimitry Andric{ 26070b57cec5SDimitry Andric return *_VSTD::min_element(__t.begin(), __t.end(), __comp); 26080b57cec5SDimitry Andric} 26090b57cec5SDimitry Andric 26100b57cec5SDimitry Andrictemplate<class _Tp> 26110b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 26120b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 26130b57cec5SDimitry Andric_Tp 26140b57cec5SDimitry Andricmin(initializer_list<_Tp> __t) 26150b57cec5SDimitry Andric{ 26160b57cec5SDimitry Andric return *_VSTD::min_element(__t.begin(), __t.end(), __less<_Tp>()); 26170b57cec5SDimitry Andric} 26180b57cec5SDimitry Andric 26190b57cec5SDimitry Andric#endif // _LIBCPP_CXX03_LANG 26200b57cec5SDimitry Andric 26210b57cec5SDimitry Andric// max_element 26220b57cec5SDimitry Andric 26230b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Compare> 26240b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 26250b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 26260b57cec5SDimitry Andric_ForwardIterator 26270b57cec5SDimitry Andricmax_element(_ForwardIterator __first, _ForwardIterator __last, _Compare __comp) 26280b57cec5SDimitry Andric{ 2629480093f4SDimitry Andric static_assert(__is_cpp17_forward_iterator<_ForwardIterator>::value, 26300b57cec5SDimitry Andric "std::max_element requires a ForwardIterator"); 26310b57cec5SDimitry Andric if (__first != __last) 26320b57cec5SDimitry Andric { 26330b57cec5SDimitry Andric _ForwardIterator __i = __first; 26340b57cec5SDimitry Andric while (++__i != __last) 26350b57cec5SDimitry Andric if (__comp(*__first, *__i)) 26360b57cec5SDimitry Andric __first = __i; 26370b57cec5SDimitry Andric } 26380b57cec5SDimitry Andric return __first; 26390b57cec5SDimitry Andric} 26400b57cec5SDimitry Andric 26410b57cec5SDimitry Andric 26420b57cec5SDimitry Andrictemplate <class _ForwardIterator> 26430b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 26440b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 26450b57cec5SDimitry Andric_ForwardIterator 26460b57cec5SDimitry Andricmax_element(_ForwardIterator __first, _ForwardIterator __last) 26470b57cec5SDimitry Andric{ 26480b57cec5SDimitry Andric return _VSTD::max_element(__first, __last, 26490b57cec5SDimitry Andric __less<typename iterator_traits<_ForwardIterator>::value_type>()); 26500b57cec5SDimitry Andric} 26510b57cec5SDimitry Andric 26520b57cec5SDimitry Andric// max 26530b57cec5SDimitry Andric 26540b57cec5SDimitry Andrictemplate <class _Tp, class _Compare> 26550b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 26560b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 26570b57cec5SDimitry Andricconst _Tp& 26580b57cec5SDimitry Andricmax(const _Tp& __a, const _Tp& __b, _Compare __comp) 26590b57cec5SDimitry Andric{ 26600b57cec5SDimitry Andric return __comp(__a, __b) ? __b : __a; 26610b57cec5SDimitry Andric} 26620b57cec5SDimitry Andric 26630b57cec5SDimitry Andrictemplate <class _Tp> 26640b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 26650b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 26660b57cec5SDimitry Andricconst _Tp& 26670b57cec5SDimitry Andricmax(const _Tp& __a, const _Tp& __b) 26680b57cec5SDimitry Andric{ 26690b57cec5SDimitry Andric return _VSTD::max(__a, __b, __less<_Tp>()); 26700b57cec5SDimitry Andric} 26710b57cec5SDimitry Andric 26720b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG 26730b57cec5SDimitry Andric 26740b57cec5SDimitry Andrictemplate<class _Tp, class _Compare> 26750b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 26760b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 26770b57cec5SDimitry Andric_Tp 26780b57cec5SDimitry Andricmax(initializer_list<_Tp> __t, _Compare __comp) 26790b57cec5SDimitry Andric{ 26800b57cec5SDimitry Andric return *_VSTD::max_element(__t.begin(), __t.end(), __comp); 26810b57cec5SDimitry Andric} 26820b57cec5SDimitry Andric 26830b57cec5SDimitry Andrictemplate<class _Tp> 26840b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 26850b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 26860b57cec5SDimitry Andric_Tp 26870b57cec5SDimitry Andricmax(initializer_list<_Tp> __t) 26880b57cec5SDimitry Andric{ 26890b57cec5SDimitry Andric return *_VSTD::max_element(__t.begin(), __t.end(), __less<_Tp>()); 26900b57cec5SDimitry Andric} 26910b57cec5SDimitry Andric 26920b57cec5SDimitry Andric#endif // _LIBCPP_CXX03_LANG 26930b57cec5SDimitry Andric 26940b57cec5SDimitry Andric#if _LIBCPP_STD_VER > 14 26950b57cec5SDimitry Andric// clamp 26960b57cec5SDimitry Andrictemplate<class _Tp, class _Compare> 26970b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 26980b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR 26990b57cec5SDimitry Andricconst _Tp& 27000b57cec5SDimitry Andricclamp(const _Tp& __v, const _Tp& __lo, const _Tp& __hi, _Compare __comp) 27010b57cec5SDimitry Andric{ 27020b57cec5SDimitry Andric _LIBCPP_ASSERT(!__comp(__hi, __lo), "Bad bounds passed to std::clamp"); 27030b57cec5SDimitry Andric return __comp(__v, __lo) ? __lo : __comp(__hi, __v) ? __hi : __v; 27040b57cec5SDimitry Andric 27050b57cec5SDimitry Andric} 27060b57cec5SDimitry Andric 27070b57cec5SDimitry Andrictemplate<class _Tp> 27080b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 27090b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR 27100b57cec5SDimitry Andricconst _Tp& 27110b57cec5SDimitry Andricclamp(const _Tp& __v, const _Tp& __lo, const _Tp& __hi) 27120b57cec5SDimitry Andric{ 27130b57cec5SDimitry Andric return _VSTD::clamp(__v, __lo, __hi, __less<_Tp>()); 27140b57cec5SDimitry Andric} 27150b57cec5SDimitry Andric#endif 27160b57cec5SDimitry Andric 27170b57cec5SDimitry Andric// minmax_element 27180b57cec5SDimitry Andric 27190b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Compare> 27200b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT _LIBCPP_CONSTEXPR_AFTER_CXX11 2721*e8d8bef9SDimitry Andricpair<_ForwardIterator, _ForwardIterator> 27220b57cec5SDimitry Andricminmax_element(_ForwardIterator __first, _ForwardIterator __last, _Compare __comp) 27230b57cec5SDimitry Andric{ 2724480093f4SDimitry Andric static_assert(__is_cpp17_forward_iterator<_ForwardIterator>::value, 27250b57cec5SDimitry Andric "std::minmax_element requires a ForwardIterator"); 2726*e8d8bef9SDimitry Andric pair<_ForwardIterator, _ForwardIterator> __result(__first, __first); 27270b57cec5SDimitry Andric if (__first != __last) 27280b57cec5SDimitry Andric { 27290b57cec5SDimitry Andric if (++__first != __last) 27300b57cec5SDimitry Andric { 27310b57cec5SDimitry Andric if (__comp(*__first, *__result.first)) 27320b57cec5SDimitry Andric __result.first = __first; 27330b57cec5SDimitry Andric else 27340b57cec5SDimitry Andric __result.second = __first; 27350b57cec5SDimitry Andric while (++__first != __last) 27360b57cec5SDimitry Andric { 27370b57cec5SDimitry Andric _ForwardIterator __i = __first; 27380b57cec5SDimitry Andric if (++__first == __last) 27390b57cec5SDimitry Andric { 27400b57cec5SDimitry Andric if (__comp(*__i, *__result.first)) 27410b57cec5SDimitry Andric __result.first = __i; 27420b57cec5SDimitry Andric else if (!__comp(*__i, *__result.second)) 27430b57cec5SDimitry Andric __result.second = __i; 27440b57cec5SDimitry Andric break; 27450b57cec5SDimitry Andric } 27460b57cec5SDimitry Andric else 27470b57cec5SDimitry Andric { 27480b57cec5SDimitry Andric if (__comp(*__first, *__i)) 27490b57cec5SDimitry Andric { 27500b57cec5SDimitry Andric if (__comp(*__first, *__result.first)) 27510b57cec5SDimitry Andric __result.first = __first; 27520b57cec5SDimitry Andric if (!__comp(*__i, *__result.second)) 27530b57cec5SDimitry Andric __result.second = __i; 27540b57cec5SDimitry Andric } 27550b57cec5SDimitry Andric else 27560b57cec5SDimitry Andric { 27570b57cec5SDimitry Andric if (__comp(*__i, *__result.first)) 27580b57cec5SDimitry Andric __result.first = __i; 27590b57cec5SDimitry Andric if (!__comp(*__first, *__result.second)) 27600b57cec5SDimitry Andric __result.second = __first; 27610b57cec5SDimitry Andric } 27620b57cec5SDimitry Andric } 27630b57cec5SDimitry Andric } 27640b57cec5SDimitry Andric } 27650b57cec5SDimitry Andric } 27660b57cec5SDimitry Andric return __result; 27670b57cec5SDimitry Andric} 27680b57cec5SDimitry Andric 27690b57cec5SDimitry Andrictemplate <class _ForwardIterator> 27700b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 27710b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 2772*e8d8bef9SDimitry Andricpair<_ForwardIterator, _ForwardIterator> 27730b57cec5SDimitry Andricminmax_element(_ForwardIterator __first, _ForwardIterator __last) 27740b57cec5SDimitry Andric{ 27750b57cec5SDimitry Andric return _VSTD::minmax_element(__first, __last, 27760b57cec5SDimitry Andric __less<typename iterator_traits<_ForwardIterator>::value_type>()); 27770b57cec5SDimitry Andric} 27780b57cec5SDimitry Andric 27790b57cec5SDimitry Andric// minmax 27800b57cec5SDimitry Andric 27810b57cec5SDimitry Andrictemplate<class _Tp, class _Compare> 27820b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 27830b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 27840b57cec5SDimitry Andricpair<const _Tp&, const _Tp&> 27850b57cec5SDimitry Andricminmax(const _Tp& __a, const _Tp& __b, _Compare __comp) 27860b57cec5SDimitry Andric{ 27870b57cec5SDimitry Andric return __comp(__b, __a) ? pair<const _Tp&, const _Tp&>(__b, __a) : 27880b57cec5SDimitry Andric pair<const _Tp&, const _Tp&>(__a, __b); 27890b57cec5SDimitry Andric} 27900b57cec5SDimitry Andric 27910b57cec5SDimitry Andrictemplate<class _Tp> 27920b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 27930b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 27940b57cec5SDimitry Andricpair<const _Tp&, const _Tp&> 27950b57cec5SDimitry Andricminmax(const _Tp& __a, const _Tp& __b) 27960b57cec5SDimitry Andric{ 27970b57cec5SDimitry Andric return _VSTD::minmax(__a, __b, __less<_Tp>()); 27980b57cec5SDimitry Andric} 27990b57cec5SDimitry Andric 28000b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG 28010b57cec5SDimitry Andric 28020b57cec5SDimitry Andrictemplate<class _Tp, class _Compare> 28030b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 28040b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 28050b57cec5SDimitry Andricpair<_Tp, _Tp> 28060b57cec5SDimitry Andricminmax(initializer_list<_Tp> __t, _Compare __comp) 28070b57cec5SDimitry Andric{ 28080b57cec5SDimitry Andric typedef typename initializer_list<_Tp>::const_iterator _Iter; 28090b57cec5SDimitry Andric _Iter __first = __t.begin(); 28100b57cec5SDimitry Andric _Iter __last = __t.end(); 2811*e8d8bef9SDimitry Andric pair<_Tp, _Tp> __result(*__first, *__first); 28120b57cec5SDimitry Andric 28130b57cec5SDimitry Andric ++__first; 28140b57cec5SDimitry Andric if (__t.size() % 2 == 0) 28150b57cec5SDimitry Andric { 28160b57cec5SDimitry Andric if (__comp(*__first, __result.first)) 28170b57cec5SDimitry Andric __result.first = *__first; 28180b57cec5SDimitry Andric else 28190b57cec5SDimitry Andric __result.second = *__first; 28200b57cec5SDimitry Andric ++__first; 28210b57cec5SDimitry Andric } 28220b57cec5SDimitry Andric 28230b57cec5SDimitry Andric while (__first != __last) 28240b57cec5SDimitry Andric { 28250b57cec5SDimitry Andric _Tp __prev = *__first++; 28260b57cec5SDimitry Andric if (__comp(*__first, __prev)) { 28270b57cec5SDimitry Andric if ( __comp(*__first, __result.first)) __result.first = *__first; 28280b57cec5SDimitry Andric if (!__comp(__prev, __result.second)) __result.second = __prev; 28290b57cec5SDimitry Andric } 28300b57cec5SDimitry Andric else { 28310b57cec5SDimitry Andric if ( __comp(__prev, __result.first)) __result.first = __prev; 28320b57cec5SDimitry Andric if (!__comp(*__first, __result.second)) __result.second = *__first; 28330b57cec5SDimitry Andric } 28340b57cec5SDimitry Andric 28350b57cec5SDimitry Andric __first++; 28360b57cec5SDimitry Andric } 28370b57cec5SDimitry Andric return __result; 28380b57cec5SDimitry Andric} 28390b57cec5SDimitry Andric 28400b57cec5SDimitry Andrictemplate<class _Tp> 28410b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 28420b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 28430b57cec5SDimitry Andricpair<_Tp, _Tp> 28440b57cec5SDimitry Andricminmax(initializer_list<_Tp> __t) 28450b57cec5SDimitry Andric{ 28460b57cec5SDimitry Andric return _VSTD::minmax(__t, __less<_Tp>()); 28470b57cec5SDimitry Andric} 28480b57cec5SDimitry Andric 28490b57cec5SDimitry Andric#endif // _LIBCPP_CXX03_LANG 28500b57cec5SDimitry Andric 28510b57cec5SDimitry Andric// random_shuffle 28520b57cec5SDimitry Andric 28530b57cec5SDimitry Andric// __independent_bits_engine 28540b57cec5SDimitry Andric 28550b57cec5SDimitry Andrictemplate <unsigned long long _Xp, size_t _Rp> 28560b57cec5SDimitry Andricstruct __log2_imp 28570b57cec5SDimitry Andric{ 28580b57cec5SDimitry Andric static const size_t value = _Xp & ((unsigned long long)(1) << _Rp) ? _Rp 28590b57cec5SDimitry Andric : __log2_imp<_Xp, _Rp - 1>::value; 28600b57cec5SDimitry Andric}; 28610b57cec5SDimitry Andric 28620b57cec5SDimitry Andrictemplate <unsigned long long _Xp> 28630b57cec5SDimitry Andricstruct __log2_imp<_Xp, 0> 28640b57cec5SDimitry Andric{ 28650b57cec5SDimitry Andric static const size_t value = 0; 28660b57cec5SDimitry Andric}; 28670b57cec5SDimitry Andric 28680b57cec5SDimitry Andrictemplate <size_t _Rp> 28690b57cec5SDimitry Andricstruct __log2_imp<0, _Rp> 28700b57cec5SDimitry Andric{ 28710b57cec5SDimitry Andric static const size_t value = _Rp + 1; 28720b57cec5SDimitry Andric}; 28730b57cec5SDimitry Andric 28740b57cec5SDimitry Andrictemplate <class _UIntType, _UIntType _Xp> 28750b57cec5SDimitry Andricstruct __log2 28760b57cec5SDimitry Andric{ 28770b57cec5SDimitry Andric static const size_t value = __log2_imp<_Xp, 28780b57cec5SDimitry Andric sizeof(_UIntType) * __CHAR_BIT__ - 1>::value; 28790b57cec5SDimitry Andric}; 28800b57cec5SDimitry Andric 28810b57cec5SDimitry Andrictemplate<class _Engine, class _UIntType> 28820b57cec5SDimitry Andricclass __independent_bits_engine 28830b57cec5SDimitry Andric{ 28840b57cec5SDimitry Andricpublic: 28850b57cec5SDimitry Andric // types 28860b57cec5SDimitry Andric typedef _UIntType result_type; 28870b57cec5SDimitry Andric 28880b57cec5SDimitry Andricprivate: 28890b57cec5SDimitry Andric typedef typename _Engine::result_type _Engine_result_type; 28900b57cec5SDimitry Andric typedef typename conditional 28910b57cec5SDimitry Andric < 28920b57cec5SDimitry Andric sizeof(_Engine_result_type) <= sizeof(result_type), 28930b57cec5SDimitry Andric result_type, 28940b57cec5SDimitry Andric _Engine_result_type 28950b57cec5SDimitry Andric >::type _Working_result_type; 28960b57cec5SDimitry Andric 28970b57cec5SDimitry Andric _Engine& __e_; 28980b57cec5SDimitry Andric size_t __w_; 28990b57cec5SDimitry Andric size_t __w0_; 29000b57cec5SDimitry Andric size_t __n_; 29010b57cec5SDimitry Andric size_t __n0_; 29020b57cec5SDimitry Andric _Working_result_type __y0_; 29030b57cec5SDimitry Andric _Working_result_type __y1_; 29040b57cec5SDimitry Andric _Engine_result_type __mask0_; 29050b57cec5SDimitry Andric _Engine_result_type __mask1_; 29060b57cec5SDimitry Andric 29070b57cec5SDimitry Andric#ifdef _LIBCPP_CXX03_LANG 29080b57cec5SDimitry Andric static const _Working_result_type _Rp = _Engine::_Max - _Engine::_Min 29090b57cec5SDimitry Andric + _Working_result_type(1); 29100b57cec5SDimitry Andric#else 29110b57cec5SDimitry Andric static _LIBCPP_CONSTEXPR const _Working_result_type _Rp = _Engine::max() - _Engine::min() 29120b57cec5SDimitry Andric + _Working_result_type(1); 29130b57cec5SDimitry Andric#endif 29140b57cec5SDimitry Andric static _LIBCPP_CONSTEXPR const size_t __m = __log2<_Working_result_type, _Rp>::value; 29150b57cec5SDimitry Andric static _LIBCPP_CONSTEXPR const size_t _WDt = numeric_limits<_Working_result_type>::digits; 29160b57cec5SDimitry Andric static _LIBCPP_CONSTEXPR const size_t _EDt = numeric_limits<_Engine_result_type>::digits; 29170b57cec5SDimitry Andric 29180b57cec5SDimitry Andricpublic: 29190b57cec5SDimitry Andric // constructors and seeding functions 29200b57cec5SDimitry Andric __independent_bits_engine(_Engine& __e, size_t __w); 29210b57cec5SDimitry Andric 29220b57cec5SDimitry Andric // generating functions 29230b57cec5SDimitry Andric result_type operator()() {return __eval(integral_constant<bool, _Rp != 0>());} 29240b57cec5SDimitry Andric 29250b57cec5SDimitry Andricprivate: 29260b57cec5SDimitry Andric result_type __eval(false_type); 29270b57cec5SDimitry Andric result_type __eval(true_type); 29280b57cec5SDimitry Andric}; 29290b57cec5SDimitry Andric 29300b57cec5SDimitry Andrictemplate<class _Engine, class _UIntType> 29310b57cec5SDimitry Andric__independent_bits_engine<_Engine, _UIntType> 29320b57cec5SDimitry Andric ::__independent_bits_engine(_Engine& __e, size_t __w) 29330b57cec5SDimitry Andric : __e_(__e), 29340b57cec5SDimitry Andric __w_(__w) 29350b57cec5SDimitry Andric{ 29360b57cec5SDimitry Andric __n_ = __w_ / __m + (__w_ % __m != 0); 29370b57cec5SDimitry Andric __w0_ = __w_ / __n_; 29380b57cec5SDimitry Andric if (_Rp == 0) 29390b57cec5SDimitry Andric __y0_ = _Rp; 29400b57cec5SDimitry Andric else if (__w0_ < _WDt) 29410b57cec5SDimitry Andric __y0_ = (_Rp >> __w0_) << __w0_; 29420b57cec5SDimitry Andric else 29430b57cec5SDimitry Andric __y0_ = 0; 29440b57cec5SDimitry Andric if (_Rp - __y0_ > __y0_ / __n_) 29450b57cec5SDimitry Andric { 29460b57cec5SDimitry Andric ++__n_; 29470b57cec5SDimitry Andric __w0_ = __w_ / __n_; 29480b57cec5SDimitry Andric if (__w0_ < _WDt) 29490b57cec5SDimitry Andric __y0_ = (_Rp >> __w0_) << __w0_; 29500b57cec5SDimitry Andric else 29510b57cec5SDimitry Andric __y0_ = 0; 29520b57cec5SDimitry Andric } 29530b57cec5SDimitry Andric __n0_ = __n_ - __w_ % __n_; 29540b57cec5SDimitry Andric if (__w0_ < _WDt - 1) 29550b57cec5SDimitry Andric __y1_ = (_Rp >> (__w0_ + 1)) << (__w0_ + 1); 29560b57cec5SDimitry Andric else 29570b57cec5SDimitry Andric __y1_ = 0; 29580b57cec5SDimitry Andric __mask0_ = __w0_ > 0 ? _Engine_result_type(~0) >> (_EDt - __w0_) : 29590b57cec5SDimitry Andric _Engine_result_type(0); 29600b57cec5SDimitry Andric __mask1_ = __w0_ < _EDt - 1 ? 29610b57cec5SDimitry Andric _Engine_result_type(~0) >> (_EDt - (__w0_ + 1)) : 29620b57cec5SDimitry Andric _Engine_result_type(~0); 29630b57cec5SDimitry Andric} 29640b57cec5SDimitry Andric 29650b57cec5SDimitry Andrictemplate<class _Engine, class _UIntType> 29660b57cec5SDimitry Andricinline 29670b57cec5SDimitry Andric_UIntType 29680b57cec5SDimitry Andric__independent_bits_engine<_Engine, _UIntType>::__eval(false_type) 29690b57cec5SDimitry Andric{ 29700b57cec5SDimitry Andric return static_cast<result_type>(__e_() & __mask0_); 29710b57cec5SDimitry Andric} 29720b57cec5SDimitry Andric 29730b57cec5SDimitry Andrictemplate<class _Engine, class _UIntType> 29740b57cec5SDimitry Andric_UIntType 29750b57cec5SDimitry Andric__independent_bits_engine<_Engine, _UIntType>::__eval(true_type) 29760b57cec5SDimitry Andric{ 29770b57cec5SDimitry Andric const size_t _WRt = numeric_limits<result_type>::digits; 29780b57cec5SDimitry Andric result_type _Sp = 0; 29790b57cec5SDimitry Andric for (size_t __k = 0; __k < __n0_; ++__k) 29800b57cec5SDimitry Andric { 29810b57cec5SDimitry Andric _Engine_result_type __u; 29820b57cec5SDimitry Andric do 29830b57cec5SDimitry Andric { 29840b57cec5SDimitry Andric __u = __e_() - _Engine::min(); 29850b57cec5SDimitry Andric } while (__u >= __y0_); 29860b57cec5SDimitry Andric if (__w0_ < _WRt) 29870b57cec5SDimitry Andric _Sp <<= __w0_; 29880b57cec5SDimitry Andric else 29890b57cec5SDimitry Andric _Sp = 0; 29900b57cec5SDimitry Andric _Sp += __u & __mask0_; 29910b57cec5SDimitry Andric } 29920b57cec5SDimitry Andric for (size_t __k = __n0_; __k < __n_; ++__k) 29930b57cec5SDimitry Andric { 29940b57cec5SDimitry Andric _Engine_result_type __u; 29950b57cec5SDimitry Andric do 29960b57cec5SDimitry Andric { 29970b57cec5SDimitry Andric __u = __e_() - _Engine::min(); 29980b57cec5SDimitry Andric } while (__u >= __y1_); 29990b57cec5SDimitry Andric if (__w0_ < _WRt - 1) 30000b57cec5SDimitry Andric _Sp <<= __w0_ + 1; 30010b57cec5SDimitry Andric else 30020b57cec5SDimitry Andric _Sp = 0; 30030b57cec5SDimitry Andric _Sp += __u & __mask1_; 30040b57cec5SDimitry Andric } 30050b57cec5SDimitry Andric return _Sp; 30060b57cec5SDimitry Andric} 30070b57cec5SDimitry Andric 30080b57cec5SDimitry Andric// uniform_int_distribution 30090b57cec5SDimitry Andric 30100b57cec5SDimitry Andrictemplate<class _IntType = int> 30110b57cec5SDimitry Andricclass uniform_int_distribution 30120b57cec5SDimitry Andric{ 30130b57cec5SDimitry Andricpublic: 30140b57cec5SDimitry Andric // types 30150b57cec5SDimitry Andric typedef _IntType result_type; 30160b57cec5SDimitry Andric 30170b57cec5SDimitry Andric class param_type 30180b57cec5SDimitry Andric { 30190b57cec5SDimitry Andric result_type __a_; 30200b57cec5SDimitry Andric result_type __b_; 30210b57cec5SDimitry Andric public: 30220b57cec5SDimitry Andric typedef uniform_int_distribution distribution_type; 30230b57cec5SDimitry Andric 30240b57cec5SDimitry Andric explicit param_type(result_type __a = 0, 30250b57cec5SDimitry Andric result_type __b = numeric_limits<result_type>::max()) 30260b57cec5SDimitry Andric : __a_(__a), __b_(__b) {} 30270b57cec5SDimitry Andric 30280b57cec5SDimitry Andric result_type a() const {return __a_;} 30290b57cec5SDimitry Andric result_type b() const {return __b_;} 30300b57cec5SDimitry Andric 30310b57cec5SDimitry Andric friend bool operator==(const param_type& __x, const param_type& __y) 30320b57cec5SDimitry Andric {return __x.__a_ == __y.__a_ && __x.__b_ == __y.__b_;} 30330b57cec5SDimitry Andric friend bool operator!=(const param_type& __x, const param_type& __y) 30340b57cec5SDimitry Andric {return !(__x == __y);} 30350b57cec5SDimitry Andric }; 30360b57cec5SDimitry Andric 30370b57cec5SDimitry Andricprivate: 30380b57cec5SDimitry Andric param_type __p_; 30390b57cec5SDimitry Andric 30400b57cec5SDimitry Andricpublic: 30410b57cec5SDimitry Andric // constructors and reset functions 3042*e8d8bef9SDimitry Andric#ifndef _LIBCPP_CXX03_LANG 3043*e8d8bef9SDimitry Andric uniform_int_distribution() : uniform_int_distribution(0) {} 3044*e8d8bef9SDimitry Andric explicit uniform_int_distribution( 3045*e8d8bef9SDimitry Andric result_type __a, result_type __b = numeric_limits<result_type>::max()) 3046*e8d8bef9SDimitry Andric : __p_(param_type(__a, __b)) {} 3047*e8d8bef9SDimitry Andric#else 3048*e8d8bef9SDimitry Andric explicit uniform_int_distribution( 3049*e8d8bef9SDimitry Andric result_type __a = 0, 30500b57cec5SDimitry Andric result_type __b = numeric_limits<result_type>::max()) 30510b57cec5SDimitry Andric : __p_(param_type(__a, __b)) {} 3052*e8d8bef9SDimitry Andric#endif 30530b57cec5SDimitry Andric explicit uniform_int_distribution(const param_type& __p) : __p_(__p) {} 30540b57cec5SDimitry Andric void reset() {} 30550b57cec5SDimitry Andric 30560b57cec5SDimitry Andric // generating functions 30570b57cec5SDimitry Andric template<class _URNG> result_type operator()(_URNG& __g) 30580b57cec5SDimitry Andric {return (*this)(__g, __p_);} 30590b57cec5SDimitry Andric template<class _URNG> result_type operator()(_URNG& __g, const param_type& __p); 30600b57cec5SDimitry Andric 30610b57cec5SDimitry Andric // property functions 30620b57cec5SDimitry Andric result_type a() const {return __p_.a();} 30630b57cec5SDimitry Andric result_type b() const {return __p_.b();} 30640b57cec5SDimitry Andric 30650b57cec5SDimitry Andric param_type param() const {return __p_;} 30660b57cec5SDimitry Andric void param(const param_type& __p) {__p_ = __p;} 30670b57cec5SDimitry Andric 30680b57cec5SDimitry Andric result_type min() const {return a();} 30690b57cec5SDimitry Andric result_type max() const {return b();} 30700b57cec5SDimitry Andric 30710b57cec5SDimitry Andric friend bool operator==(const uniform_int_distribution& __x, 30720b57cec5SDimitry Andric const uniform_int_distribution& __y) 30730b57cec5SDimitry Andric {return __x.__p_ == __y.__p_;} 30740b57cec5SDimitry Andric friend bool operator!=(const uniform_int_distribution& __x, 30750b57cec5SDimitry Andric const uniform_int_distribution& __y) 30760b57cec5SDimitry Andric {return !(__x == __y);} 30770b57cec5SDimitry Andric}; 30780b57cec5SDimitry Andric 30790b57cec5SDimitry Andrictemplate<class _IntType> 30800b57cec5SDimitry Andrictemplate<class _URNG> 30810b57cec5SDimitry Andrictypename uniform_int_distribution<_IntType>::result_type 30820b57cec5SDimitry Andricuniform_int_distribution<_IntType>::operator()(_URNG& __g, const param_type& __p) 30830b57cec5SDimitry Andric_LIBCPP_DISABLE_UBSAN_UNSIGNED_INTEGER_CHECK 30840b57cec5SDimitry Andric{ 30850b57cec5SDimitry Andric typedef typename conditional<sizeof(result_type) <= sizeof(uint32_t), 30860b57cec5SDimitry Andric uint32_t, uint64_t>::type _UIntType; 30870b57cec5SDimitry Andric const _UIntType _Rp = _UIntType(__p.b()) - _UIntType(__p.a()) + _UIntType(1); 30880b57cec5SDimitry Andric if (_Rp == 1) 30890b57cec5SDimitry Andric return __p.a(); 30900b57cec5SDimitry Andric const size_t _Dt = numeric_limits<_UIntType>::digits; 30910b57cec5SDimitry Andric typedef __independent_bits_engine<_URNG, _UIntType> _Eng; 30920b57cec5SDimitry Andric if (_Rp == 0) 30930b57cec5SDimitry Andric return static_cast<result_type>(_Eng(__g, _Dt)()); 30940b57cec5SDimitry Andric size_t __w = _Dt - __libcpp_clz(_Rp) - 1; 3095*e8d8bef9SDimitry Andric if ((_Rp & (numeric_limits<_UIntType>::max() >> (_Dt - __w))) != 0) 30960b57cec5SDimitry Andric ++__w; 30970b57cec5SDimitry Andric _Eng __e(__g, __w); 30980b57cec5SDimitry Andric _UIntType __u; 30990b57cec5SDimitry Andric do 31000b57cec5SDimitry Andric { 31010b57cec5SDimitry Andric __u = __e(); 31020b57cec5SDimitry Andric } while (__u >= _Rp); 31030b57cec5SDimitry Andric return static_cast<result_type>(__u + __p.a()); 31040b57cec5SDimitry Andric} 31050b57cec5SDimitry Andric 31060b57cec5SDimitry Andric#if _LIBCPP_STD_VER <= 14 || defined(_LIBCPP_ENABLE_CXX17_REMOVED_RANDOM_SHUFFLE) \ 31070b57cec5SDimitry Andric || defined(_LIBCPP_BUILDING_LIBRARY) 31080b57cec5SDimitry Andricclass _LIBCPP_TYPE_VIS __rs_default; 31090b57cec5SDimitry Andric 31100b57cec5SDimitry Andric_LIBCPP_FUNC_VIS __rs_default __rs_get(); 31110b57cec5SDimitry Andric 31120b57cec5SDimitry Andricclass _LIBCPP_TYPE_VIS __rs_default 31130b57cec5SDimitry Andric{ 31140b57cec5SDimitry Andric static unsigned __c_; 31150b57cec5SDimitry Andric 31160b57cec5SDimitry Andric __rs_default(); 31170b57cec5SDimitry Andricpublic: 31180b57cec5SDimitry Andric typedef uint_fast32_t result_type; 31190b57cec5SDimitry Andric 31200b57cec5SDimitry Andric static const result_type _Min = 0; 31210b57cec5SDimitry Andric static const result_type _Max = 0xFFFFFFFF; 31220b57cec5SDimitry Andric 31230b57cec5SDimitry Andric __rs_default(const __rs_default&); 31240b57cec5SDimitry Andric ~__rs_default(); 31250b57cec5SDimitry Andric 31260b57cec5SDimitry Andric result_type operator()(); 31270b57cec5SDimitry Andric 31280b57cec5SDimitry Andric static _LIBCPP_CONSTEXPR result_type min() {return _Min;} 31290b57cec5SDimitry Andric static _LIBCPP_CONSTEXPR result_type max() {return _Max;} 31300b57cec5SDimitry Andric 31310b57cec5SDimitry Andric friend _LIBCPP_FUNC_VIS __rs_default __rs_get(); 31320b57cec5SDimitry Andric}; 31330b57cec5SDimitry Andric 31340b57cec5SDimitry Andric_LIBCPP_FUNC_VIS __rs_default __rs_get(); 31350b57cec5SDimitry Andric 31360b57cec5SDimitry Andrictemplate <class _RandomAccessIterator> 31370b57cec5SDimitry Andric_LIBCPP_DEPRECATED_IN_CXX14 void 31380b57cec5SDimitry Andricrandom_shuffle(_RandomAccessIterator __first, _RandomAccessIterator __last) 31390b57cec5SDimitry Andric{ 31400b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::difference_type difference_type; 31410b57cec5SDimitry Andric typedef uniform_int_distribution<ptrdiff_t> _Dp; 31420b57cec5SDimitry Andric typedef typename _Dp::param_type _Pp; 31430b57cec5SDimitry Andric difference_type __d = __last - __first; 31440b57cec5SDimitry Andric if (__d > 1) 31450b57cec5SDimitry Andric { 31460b57cec5SDimitry Andric _Dp __uid; 31470b57cec5SDimitry Andric __rs_default __g = __rs_get(); 31480b57cec5SDimitry Andric for (--__last, (void) --__d; __first < __last; ++__first, (void) --__d) 31490b57cec5SDimitry Andric { 31500b57cec5SDimitry Andric difference_type __i = __uid(__g, _Pp(0, __d)); 31510b57cec5SDimitry Andric if (__i != difference_type(0)) 31520b57cec5SDimitry Andric swap(*__first, *(__first + __i)); 31530b57cec5SDimitry Andric } 31540b57cec5SDimitry Andric } 31550b57cec5SDimitry Andric} 31560b57cec5SDimitry Andric 31570b57cec5SDimitry Andrictemplate <class _RandomAccessIterator, class _RandomNumberGenerator> 31580b57cec5SDimitry Andric_LIBCPP_DEPRECATED_IN_CXX14 void 31590b57cec5SDimitry Andricrandom_shuffle(_RandomAccessIterator __first, _RandomAccessIterator __last, 31600b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG 31610b57cec5SDimitry Andric _RandomNumberGenerator&& __rand) 31620b57cec5SDimitry Andric#else 31630b57cec5SDimitry Andric _RandomNumberGenerator& __rand) 31640b57cec5SDimitry Andric#endif 31650b57cec5SDimitry Andric{ 31660b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::difference_type difference_type; 31670b57cec5SDimitry Andric difference_type __d = __last - __first; 31680b57cec5SDimitry Andric if (__d > 1) 31690b57cec5SDimitry Andric { 31700b57cec5SDimitry Andric for (--__last; __first < __last; ++__first, (void) --__d) 31710b57cec5SDimitry Andric { 31720b57cec5SDimitry Andric difference_type __i = __rand(__d); 31730b57cec5SDimitry Andric if (__i != difference_type(0)) 31740b57cec5SDimitry Andric swap(*__first, *(__first + __i)); 31750b57cec5SDimitry Andric } 31760b57cec5SDimitry Andric } 31770b57cec5SDimitry Andric} 31780b57cec5SDimitry Andric#endif 31790b57cec5SDimitry Andric 31800b57cec5SDimitry Andrictemplate <class _PopulationIterator, class _SampleIterator, class _Distance, 31810b57cec5SDimitry Andric class _UniformRandomNumberGenerator> 31820b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY 31830b57cec5SDimitry Andric_SampleIterator __sample(_PopulationIterator __first, 31840b57cec5SDimitry Andric _PopulationIterator __last, _SampleIterator __output_iter, 31850b57cec5SDimitry Andric _Distance __n, 31860b57cec5SDimitry Andric _UniformRandomNumberGenerator & __g, 31870b57cec5SDimitry Andric input_iterator_tag) { 31880b57cec5SDimitry Andric 31890b57cec5SDimitry Andric _Distance __k = 0; 31900b57cec5SDimitry Andric for (; __first != __last && __k < __n; ++__first, (void) ++__k) 31910b57cec5SDimitry Andric __output_iter[__k] = *__first; 31920b57cec5SDimitry Andric _Distance __sz = __k; 31930b57cec5SDimitry Andric for (; __first != __last; ++__first, (void) ++__k) { 31940b57cec5SDimitry Andric _Distance __r = _VSTD::uniform_int_distribution<_Distance>(0, __k)(__g); 31950b57cec5SDimitry Andric if (__r < __sz) 31960b57cec5SDimitry Andric __output_iter[__r] = *__first; 31970b57cec5SDimitry Andric } 31980b57cec5SDimitry Andric return __output_iter + _VSTD::min(__n, __k); 31990b57cec5SDimitry Andric} 32000b57cec5SDimitry Andric 32010b57cec5SDimitry Andrictemplate <class _PopulationIterator, class _SampleIterator, class _Distance, 32020b57cec5SDimitry Andric class _UniformRandomNumberGenerator> 32030b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY 32040b57cec5SDimitry Andric_SampleIterator __sample(_PopulationIterator __first, 32050b57cec5SDimitry Andric _PopulationIterator __last, _SampleIterator __output_iter, 32060b57cec5SDimitry Andric _Distance __n, 32070b57cec5SDimitry Andric _UniformRandomNumberGenerator& __g, 32080b57cec5SDimitry Andric forward_iterator_tag) { 32090b57cec5SDimitry Andric _Distance __unsampled_sz = _VSTD::distance(__first, __last); 32100b57cec5SDimitry Andric for (__n = _VSTD::min(__n, __unsampled_sz); __n != 0; ++__first) { 32110b57cec5SDimitry Andric _Distance __r = 32120b57cec5SDimitry Andric _VSTD::uniform_int_distribution<_Distance>(0, --__unsampled_sz)(__g); 32130b57cec5SDimitry Andric if (__r < __n) { 32140b57cec5SDimitry Andric *__output_iter++ = *__first; 32150b57cec5SDimitry Andric --__n; 32160b57cec5SDimitry Andric } 32170b57cec5SDimitry Andric } 32180b57cec5SDimitry Andric return __output_iter; 32190b57cec5SDimitry Andric} 32200b57cec5SDimitry Andric 32210b57cec5SDimitry Andrictemplate <class _PopulationIterator, class _SampleIterator, class _Distance, 32220b57cec5SDimitry Andric class _UniformRandomNumberGenerator> 32230b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY 32240b57cec5SDimitry Andric_SampleIterator __sample(_PopulationIterator __first, 32250b57cec5SDimitry Andric _PopulationIterator __last, _SampleIterator __output_iter, 32260b57cec5SDimitry Andric _Distance __n, _UniformRandomNumberGenerator& __g) { 32270b57cec5SDimitry Andric typedef typename iterator_traits<_PopulationIterator>::iterator_category 32280b57cec5SDimitry Andric _PopCategory; 32290b57cec5SDimitry Andric typedef typename iterator_traits<_PopulationIterator>::difference_type 32300b57cec5SDimitry Andric _Difference; 3231480093f4SDimitry Andric static_assert(__is_cpp17_forward_iterator<_PopulationIterator>::value || 3232480093f4SDimitry Andric __is_cpp17_random_access_iterator<_SampleIterator>::value, 32330b57cec5SDimitry Andric "SampleIterator must meet the requirements of RandomAccessIterator"); 32340b57cec5SDimitry Andric typedef typename common_type<_Distance, _Difference>::type _CommonType; 32350b57cec5SDimitry Andric _LIBCPP_ASSERT(__n >= 0, "N must be a positive number."); 32360b57cec5SDimitry Andric return _VSTD::__sample( 32370b57cec5SDimitry Andric __first, __last, __output_iter, _CommonType(__n), 32380b57cec5SDimitry Andric __g, _PopCategory()); 32390b57cec5SDimitry Andric} 32400b57cec5SDimitry Andric 32410b57cec5SDimitry Andric#if _LIBCPP_STD_VER > 14 32420b57cec5SDimitry Andrictemplate <class _PopulationIterator, class _SampleIterator, class _Distance, 32430b57cec5SDimitry Andric class _UniformRandomNumberGenerator> 32440b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 32450b57cec5SDimitry Andric_SampleIterator sample(_PopulationIterator __first, 32460b57cec5SDimitry Andric _PopulationIterator __last, _SampleIterator __output_iter, 32470b57cec5SDimitry Andric _Distance __n, _UniformRandomNumberGenerator&& __g) { 32480b57cec5SDimitry Andric return _VSTD::__sample(__first, __last, __output_iter, __n, __g); 32490b57cec5SDimitry Andric} 32500b57cec5SDimitry Andric#endif // _LIBCPP_STD_VER > 14 32510b57cec5SDimitry Andric 32520b57cec5SDimitry Andrictemplate<class _RandomAccessIterator, class _UniformRandomNumberGenerator> 32530b57cec5SDimitry Andric void shuffle(_RandomAccessIterator __first, _RandomAccessIterator __last, 32540b57cec5SDimitry Andric _UniformRandomNumberGenerator&& __g) 32550b57cec5SDimitry Andric{ 32560b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::difference_type difference_type; 32570b57cec5SDimitry Andric typedef uniform_int_distribution<ptrdiff_t> _Dp; 32580b57cec5SDimitry Andric typedef typename _Dp::param_type _Pp; 32590b57cec5SDimitry Andric difference_type __d = __last - __first; 32600b57cec5SDimitry Andric if (__d > 1) 32610b57cec5SDimitry Andric { 32620b57cec5SDimitry Andric _Dp __uid; 3263e40139ffSDimitry Andric for (--__last, (void) --__d; __first < __last; ++__first, (void) --__d) 32640b57cec5SDimitry Andric { 32650b57cec5SDimitry Andric difference_type __i = __uid(__g, _Pp(0, __d)); 32660b57cec5SDimitry Andric if (__i != difference_type(0)) 32670b57cec5SDimitry Andric swap(*__first, *(__first + __i)); 32680b57cec5SDimitry Andric } 32690b57cec5SDimitry Andric } 32700b57cec5SDimitry Andric} 32710b57cec5SDimitry Andric 3272*e8d8bef9SDimitry Andric#if _LIBCPP_STD_VER > 17 3273*e8d8bef9SDimitry Andric 3274*e8d8bef9SDimitry Andric// shift_left, shift_right 3275*e8d8bef9SDimitry Andric 3276*e8d8bef9SDimitry Andrictemplate <class _ForwardIterator> 3277*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY constexpr 3278*e8d8bef9SDimitry Andric_ForwardIterator 3279*e8d8bef9SDimitry Andricshift_left(_ForwardIterator __first, _ForwardIterator __last, 3280*e8d8bef9SDimitry Andric typename iterator_traits<_ForwardIterator>::difference_type __n) 3281*e8d8bef9SDimitry Andric{ 3282*e8d8bef9SDimitry Andric if (__n == 0) { 3283*e8d8bef9SDimitry Andric return __last; 3284*e8d8bef9SDimitry Andric } 3285*e8d8bef9SDimitry Andric 3286*e8d8bef9SDimitry Andric _ForwardIterator __m = __first; 3287*e8d8bef9SDimitry Andric if constexpr (__is_cpp17_random_access_iterator<_ForwardIterator>::value) { 3288*e8d8bef9SDimitry Andric if (__n >= __last - __first) { 3289*e8d8bef9SDimitry Andric return __first; 3290*e8d8bef9SDimitry Andric } 3291*e8d8bef9SDimitry Andric __m += __n; 3292*e8d8bef9SDimitry Andric } else { 3293*e8d8bef9SDimitry Andric for (; __n > 0; --__n) { 3294*e8d8bef9SDimitry Andric if (__m == __last) { 3295*e8d8bef9SDimitry Andric return __first; 3296*e8d8bef9SDimitry Andric } 3297*e8d8bef9SDimitry Andric ++__m; 3298*e8d8bef9SDimitry Andric } 3299*e8d8bef9SDimitry Andric } 3300*e8d8bef9SDimitry Andric return _VSTD::move(__m, __last, __first); 3301*e8d8bef9SDimitry Andric} 3302*e8d8bef9SDimitry Andric 3303*e8d8bef9SDimitry Andrictemplate <class _ForwardIterator> 3304*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY constexpr 3305*e8d8bef9SDimitry Andric_ForwardIterator 3306*e8d8bef9SDimitry Andricshift_right(_ForwardIterator __first, _ForwardIterator __last, 3307*e8d8bef9SDimitry Andric typename iterator_traits<_ForwardIterator>::difference_type __n) 3308*e8d8bef9SDimitry Andric{ 3309*e8d8bef9SDimitry Andric if (__n == 0) { 3310*e8d8bef9SDimitry Andric return __first; 3311*e8d8bef9SDimitry Andric } 3312*e8d8bef9SDimitry Andric 3313*e8d8bef9SDimitry Andric if constexpr (__is_cpp17_random_access_iterator<_ForwardIterator>::value) { 3314*e8d8bef9SDimitry Andric decltype(__n) __d = __last - __first; 3315*e8d8bef9SDimitry Andric if (__n >= __d) { 3316*e8d8bef9SDimitry Andric return __last; 3317*e8d8bef9SDimitry Andric } 3318*e8d8bef9SDimitry Andric _ForwardIterator __m = __first + (__d - __n); 3319*e8d8bef9SDimitry Andric return _VSTD::move_backward(__first, __m, __last); 3320*e8d8bef9SDimitry Andric } else if constexpr (__is_cpp17_bidirectional_iterator<_ForwardIterator>::value) { 3321*e8d8bef9SDimitry Andric _ForwardIterator __m = __last; 3322*e8d8bef9SDimitry Andric for (; __n > 0; --__n) { 3323*e8d8bef9SDimitry Andric if (__m == __first) { 3324*e8d8bef9SDimitry Andric return __last; 3325*e8d8bef9SDimitry Andric } 3326*e8d8bef9SDimitry Andric --__m; 3327*e8d8bef9SDimitry Andric } 3328*e8d8bef9SDimitry Andric return _VSTD::move_backward(__first, __m, __last); 3329*e8d8bef9SDimitry Andric } else { 3330*e8d8bef9SDimitry Andric _ForwardIterator __ret = __first; 3331*e8d8bef9SDimitry Andric for (; __n > 0; --__n) { 3332*e8d8bef9SDimitry Andric if (__ret == __last) { 3333*e8d8bef9SDimitry Andric return __last; 3334*e8d8bef9SDimitry Andric } 3335*e8d8bef9SDimitry Andric ++__ret; 3336*e8d8bef9SDimitry Andric } 3337*e8d8bef9SDimitry Andric 3338*e8d8bef9SDimitry Andric // We have an __n-element scratch space from __first to __ret. 3339*e8d8bef9SDimitry Andric // Slide an __n-element window [__trail, __lead) from left to right. 3340*e8d8bef9SDimitry Andric // We're essentially doing swap_ranges(__first, __ret, __trail, __lead) 3341*e8d8bef9SDimitry Andric // over and over; but once __lead reaches __last we needn't bother 3342*e8d8bef9SDimitry Andric // to save the values of elements [__trail, __last). 3343*e8d8bef9SDimitry Andric 3344*e8d8bef9SDimitry Andric auto __trail = __first; 3345*e8d8bef9SDimitry Andric auto __lead = __ret; 3346*e8d8bef9SDimitry Andric while (__trail != __ret) { 3347*e8d8bef9SDimitry Andric if (__lead == __last) { 3348*e8d8bef9SDimitry Andric _VSTD::move(__first, __trail, __ret); 3349*e8d8bef9SDimitry Andric return __ret; 3350*e8d8bef9SDimitry Andric } 3351*e8d8bef9SDimitry Andric ++__trail; 3352*e8d8bef9SDimitry Andric ++__lead; 3353*e8d8bef9SDimitry Andric } 3354*e8d8bef9SDimitry Andric 3355*e8d8bef9SDimitry Andric _ForwardIterator __mid = __first; 3356*e8d8bef9SDimitry Andric while (true) { 3357*e8d8bef9SDimitry Andric if (__lead == __last) { 3358*e8d8bef9SDimitry Andric __trail = _VSTD::move(__mid, __ret, __trail); 3359*e8d8bef9SDimitry Andric _VSTD::move(__first, __mid, __trail); 3360*e8d8bef9SDimitry Andric return __ret; 3361*e8d8bef9SDimitry Andric } 3362*e8d8bef9SDimitry Andric swap(*__mid, *__trail); 3363*e8d8bef9SDimitry Andric ++__mid; 3364*e8d8bef9SDimitry Andric ++__trail; 3365*e8d8bef9SDimitry Andric ++__lead; 3366*e8d8bef9SDimitry Andric if (__mid == __ret) { 3367*e8d8bef9SDimitry Andric __mid = __first; 3368*e8d8bef9SDimitry Andric } 3369*e8d8bef9SDimitry Andric } 3370*e8d8bef9SDimitry Andric } 3371*e8d8bef9SDimitry Andric} 3372*e8d8bef9SDimitry Andric 3373*e8d8bef9SDimitry Andric#endif // _LIBCPP_STD_VER > 17 3374*e8d8bef9SDimitry Andric 3375*e8d8bef9SDimitry Andric// is_partitioned 3376*e8d8bef9SDimitry Andric 33770b57cec5SDimitry Andrictemplate <class _InputIterator, class _Predicate> 33780b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT _LIBCPP_CONSTEXPR_AFTER_CXX17 bool 33790b57cec5SDimitry Andricis_partitioned(_InputIterator __first, _InputIterator __last, _Predicate __pred) 33800b57cec5SDimitry Andric{ 33810b57cec5SDimitry Andric for (; __first != __last; ++__first) 33820b57cec5SDimitry Andric if (!__pred(*__first)) 33830b57cec5SDimitry Andric break; 33840b57cec5SDimitry Andric if ( __first == __last ) 33850b57cec5SDimitry Andric return true; 33860b57cec5SDimitry Andric ++__first; 33870b57cec5SDimitry Andric for (; __first != __last; ++__first) 33880b57cec5SDimitry Andric if (__pred(*__first)) 33890b57cec5SDimitry Andric return false; 33900b57cec5SDimitry Andric return true; 33910b57cec5SDimitry Andric} 33920b57cec5SDimitry Andric 33930b57cec5SDimitry Andric// partition 33940b57cec5SDimitry Andric 33950b57cec5SDimitry Andrictemplate <class _Predicate, class _ForwardIterator> 3396*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _ForwardIterator 33970b57cec5SDimitry Andric__partition(_ForwardIterator __first, _ForwardIterator __last, _Predicate __pred, forward_iterator_tag) 33980b57cec5SDimitry Andric{ 33990b57cec5SDimitry Andric while (true) 34000b57cec5SDimitry Andric { 34010b57cec5SDimitry Andric if (__first == __last) 34020b57cec5SDimitry Andric return __first; 34030b57cec5SDimitry Andric if (!__pred(*__first)) 34040b57cec5SDimitry Andric break; 34050b57cec5SDimitry Andric ++__first; 34060b57cec5SDimitry Andric } 34070b57cec5SDimitry Andric for (_ForwardIterator __p = __first; ++__p != __last;) 34080b57cec5SDimitry Andric { 34090b57cec5SDimitry Andric if (__pred(*__p)) 34100b57cec5SDimitry Andric { 34110b57cec5SDimitry Andric swap(*__first, *__p); 34120b57cec5SDimitry Andric ++__first; 34130b57cec5SDimitry Andric } 34140b57cec5SDimitry Andric } 34150b57cec5SDimitry Andric return __first; 34160b57cec5SDimitry Andric} 34170b57cec5SDimitry Andric 34180b57cec5SDimitry Andrictemplate <class _Predicate, class _BidirectionalIterator> 3419*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _BidirectionalIterator 34200b57cec5SDimitry Andric__partition(_BidirectionalIterator __first, _BidirectionalIterator __last, _Predicate __pred, 34210b57cec5SDimitry Andric bidirectional_iterator_tag) 34220b57cec5SDimitry Andric{ 34230b57cec5SDimitry Andric while (true) 34240b57cec5SDimitry Andric { 34250b57cec5SDimitry Andric while (true) 34260b57cec5SDimitry Andric { 34270b57cec5SDimitry Andric if (__first == __last) 34280b57cec5SDimitry Andric return __first; 34290b57cec5SDimitry Andric if (!__pred(*__first)) 34300b57cec5SDimitry Andric break; 34310b57cec5SDimitry Andric ++__first; 34320b57cec5SDimitry Andric } 34330b57cec5SDimitry Andric do 34340b57cec5SDimitry Andric { 34350b57cec5SDimitry Andric if (__first == --__last) 34360b57cec5SDimitry Andric return __first; 34370b57cec5SDimitry Andric } while (!__pred(*__last)); 34380b57cec5SDimitry Andric swap(*__first, *__last); 34390b57cec5SDimitry Andric ++__first; 34400b57cec5SDimitry Andric } 34410b57cec5SDimitry Andric} 34420b57cec5SDimitry Andric 34430b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Predicate> 3444*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 34450b57cec5SDimitry Andric_ForwardIterator 34460b57cec5SDimitry Andricpartition(_ForwardIterator __first, _ForwardIterator __last, _Predicate __pred) 34470b57cec5SDimitry Andric{ 34480b57cec5SDimitry Andric return _VSTD::__partition<typename add_lvalue_reference<_Predicate>::type> 34490b57cec5SDimitry Andric (__first, __last, __pred, typename iterator_traits<_ForwardIterator>::iterator_category()); 34500b57cec5SDimitry Andric} 34510b57cec5SDimitry Andric 34520b57cec5SDimitry Andric// partition_copy 34530b57cec5SDimitry Andric 34540b57cec5SDimitry Andrictemplate <class _InputIterator, class _OutputIterator1, 34550b57cec5SDimitry Andric class _OutputIterator2, class _Predicate> 34560b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 pair<_OutputIterator1, _OutputIterator2> 34570b57cec5SDimitry Andricpartition_copy(_InputIterator __first, _InputIterator __last, 34580b57cec5SDimitry Andric _OutputIterator1 __out_true, _OutputIterator2 __out_false, 34590b57cec5SDimitry Andric _Predicate __pred) 34600b57cec5SDimitry Andric{ 34610b57cec5SDimitry Andric for (; __first != __last; ++__first) 34620b57cec5SDimitry Andric { 34630b57cec5SDimitry Andric if (__pred(*__first)) 34640b57cec5SDimitry Andric { 34650b57cec5SDimitry Andric *__out_true = *__first; 34660b57cec5SDimitry Andric ++__out_true; 34670b57cec5SDimitry Andric } 34680b57cec5SDimitry Andric else 34690b57cec5SDimitry Andric { 34700b57cec5SDimitry Andric *__out_false = *__first; 34710b57cec5SDimitry Andric ++__out_false; 34720b57cec5SDimitry Andric } 34730b57cec5SDimitry Andric } 34740b57cec5SDimitry Andric return pair<_OutputIterator1, _OutputIterator2>(__out_true, __out_false); 34750b57cec5SDimitry Andric} 34760b57cec5SDimitry Andric 34770b57cec5SDimitry Andric// partition_point 34780b57cec5SDimitry Andric 34790b57cec5SDimitry Andrictemplate<class _ForwardIterator, class _Predicate> 34800b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _ForwardIterator 34810b57cec5SDimitry Andricpartition_point(_ForwardIterator __first, _ForwardIterator __last, _Predicate __pred) 34820b57cec5SDimitry Andric{ 34830b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator>::difference_type difference_type; 34840b57cec5SDimitry Andric difference_type __len = _VSTD::distance(__first, __last); 34850b57cec5SDimitry Andric while (__len != 0) 34860b57cec5SDimitry Andric { 34870b57cec5SDimitry Andric difference_type __l2 = _VSTD::__half_positive(__len); 34880b57cec5SDimitry Andric _ForwardIterator __m = __first; 34890b57cec5SDimitry Andric _VSTD::advance(__m, __l2); 34900b57cec5SDimitry Andric if (__pred(*__m)) 34910b57cec5SDimitry Andric { 34920b57cec5SDimitry Andric __first = ++__m; 34930b57cec5SDimitry Andric __len -= __l2 + 1; 34940b57cec5SDimitry Andric } 34950b57cec5SDimitry Andric else 34960b57cec5SDimitry Andric __len = __l2; 34970b57cec5SDimitry Andric } 34980b57cec5SDimitry Andric return __first; 34990b57cec5SDimitry Andric} 35000b57cec5SDimitry Andric 35010b57cec5SDimitry Andric// stable_partition 35020b57cec5SDimitry Andric 35030b57cec5SDimitry Andrictemplate <class _Predicate, class _ForwardIterator, class _Distance, class _Pair> 35040b57cec5SDimitry Andric_ForwardIterator 35050b57cec5SDimitry Andric__stable_partition(_ForwardIterator __first, _ForwardIterator __last, _Predicate __pred, 35060b57cec5SDimitry Andric _Distance __len, _Pair __p, forward_iterator_tag __fit) 35070b57cec5SDimitry Andric{ 35080b57cec5SDimitry Andric // *__first is known to be false 35090b57cec5SDimitry Andric // __len >= 1 35100b57cec5SDimitry Andric if (__len == 1) 35110b57cec5SDimitry Andric return __first; 35120b57cec5SDimitry Andric if (__len == 2) 35130b57cec5SDimitry Andric { 35140b57cec5SDimitry Andric _ForwardIterator __m = __first; 35150b57cec5SDimitry Andric if (__pred(*++__m)) 35160b57cec5SDimitry Andric { 35170b57cec5SDimitry Andric swap(*__first, *__m); 35180b57cec5SDimitry Andric return __m; 35190b57cec5SDimitry Andric } 35200b57cec5SDimitry Andric return __first; 35210b57cec5SDimitry Andric } 35220b57cec5SDimitry Andric if (__len <= __p.second) 35230b57cec5SDimitry Andric { // The buffer is big enough to use 35240b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator>::value_type value_type; 35250b57cec5SDimitry Andric __destruct_n __d(0); 35260b57cec5SDimitry Andric unique_ptr<value_type, __destruct_n&> __h(__p.first, __d); 35270b57cec5SDimitry Andric // Move the falses into the temporary buffer, and the trues to the front of the line 35280b57cec5SDimitry Andric // Update __first to always point to the end of the trues 35290b57cec5SDimitry Andric value_type* __t = __p.first; 3530*e8d8bef9SDimitry Andric ::new ((void*)__t) value_type(_VSTD::move(*__first)); 3531*e8d8bef9SDimitry Andric __d.template __incr<value_type>(); 35320b57cec5SDimitry Andric ++__t; 35330b57cec5SDimitry Andric _ForwardIterator __i = __first; 35340b57cec5SDimitry Andric while (++__i != __last) 35350b57cec5SDimitry Andric { 35360b57cec5SDimitry Andric if (__pred(*__i)) 35370b57cec5SDimitry Andric { 35380b57cec5SDimitry Andric *__first = _VSTD::move(*__i); 35390b57cec5SDimitry Andric ++__first; 35400b57cec5SDimitry Andric } 35410b57cec5SDimitry Andric else 35420b57cec5SDimitry Andric { 3543*e8d8bef9SDimitry Andric ::new ((void*)__t) value_type(_VSTD::move(*__i)); 3544*e8d8bef9SDimitry Andric __d.template __incr<value_type>(); 35450b57cec5SDimitry Andric ++__t; 35460b57cec5SDimitry Andric } 35470b57cec5SDimitry Andric } 35480b57cec5SDimitry Andric // All trues now at start of range, all falses in buffer 35490b57cec5SDimitry Andric // Move falses back into range, but don't mess up __first which points to first false 35500b57cec5SDimitry Andric __i = __first; 3551e40139ffSDimitry Andric for (value_type* __t2 = __p.first; __t2 < __t; ++__t2, (void) ++__i) 35520b57cec5SDimitry Andric *__i = _VSTD::move(*__t2); 35530b57cec5SDimitry Andric // __h destructs moved-from values out of the temp buffer, but doesn't deallocate buffer 35540b57cec5SDimitry Andric return __first; 35550b57cec5SDimitry Andric } 35560b57cec5SDimitry Andric // Else not enough buffer, do in place 35570b57cec5SDimitry Andric // __len >= 3 35580b57cec5SDimitry Andric _ForwardIterator __m = __first; 35590b57cec5SDimitry Andric _Distance __len2 = __len / 2; // __len2 >= 2 35600b57cec5SDimitry Andric _VSTD::advance(__m, __len2); 35610b57cec5SDimitry Andric // recurse on [__first, __m), *__first know to be false 35620b57cec5SDimitry Andric // F????????????????? 35630b57cec5SDimitry Andric // f m l 35640b57cec5SDimitry Andric typedef typename add_lvalue_reference<_Predicate>::type _PredRef; 3565*e8d8bef9SDimitry Andric _ForwardIterator __first_false = _VSTD::__stable_partition<_PredRef>(__first, __m, __pred, __len2, __p, __fit); 35660b57cec5SDimitry Andric // TTTFFFFF?????????? 35670b57cec5SDimitry Andric // f ff m l 35680b57cec5SDimitry Andric // recurse on [__m, __last], except increase __m until *(__m) is false, *__last know to be true 35690b57cec5SDimitry Andric _ForwardIterator __m1 = __m; 35700b57cec5SDimitry Andric _ForwardIterator __second_false = __last; 35710b57cec5SDimitry Andric _Distance __len_half = __len - __len2; 35720b57cec5SDimitry Andric while (__pred(*__m1)) 35730b57cec5SDimitry Andric { 35740b57cec5SDimitry Andric if (++__m1 == __last) 35750b57cec5SDimitry Andric goto __second_half_done; 35760b57cec5SDimitry Andric --__len_half; 35770b57cec5SDimitry Andric } 35780b57cec5SDimitry Andric // TTTFFFFFTTTF?????? 35790b57cec5SDimitry Andric // f ff m m1 l 3580*e8d8bef9SDimitry Andric __second_false = _VSTD::__stable_partition<_PredRef>(__m1, __last, __pred, __len_half, __p, __fit); 35810b57cec5SDimitry Andric__second_half_done: 35820b57cec5SDimitry Andric // TTTFFFFFTTTTTFFFFF 35830b57cec5SDimitry Andric // f ff m sf l 35840b57cec5SDimitry Andric return _VSTD::rotate(__first_false, __m, __second_false); 35850b57cec5SDimitry Andric // TTTTTTTTFFFFFFFFFF 35860b57cec5SDimitry Andric // | 35870b57cec5SDimitry Andric} 35880b57cec5SDimitry Andric 35890b57cec5SDimitry Andricstruct __return_temporary_buffer 35900b57cec5SDimitry Andric{ 35910b57cec5SDimitry Andric template <class _Tp> 35920b57cec5SDimitry Andric _LIBCPP_INLINE_VISIBILITY void operator()(_Tp* __p) const {_VSTD::return_temporary_buffer(__p);} 35930b57cec5SDimitry Andric}; 35940b57cec5SDimitry Andric 35950b57cec5SDimitry Andrictemplate <class _Predicate, class _ForwardIterator> 35960b57cec5SDimitry Andric_ForwardIterator 35970b57cec5SDimitry Andric__stable_partition(_ForwardIterator __first, _ForwardIterator __last, _Predicate __pred, 35980b57cec5SDimitry Andric forward_iterator_tag) 35990b57cec5SDimitry Andric{ 36000b57cec5SDimitry Andric const unsigned __alloc_limit = 3; // might want to make this a function of trivial assignment 36010b57cec5SDimitry Andric // Either prove all true and return __first or point to first false 36020b57cec5SDimitry Andric while (true) 36030b57cec5SDimitry Andric { 36040b57cec5SDimitry Andric if (__first == __last) 36050b57cec5SDimitry Andric return __first; 36060b57cec5SDimitry Andric if (!__pred(*__first)) 36070b57cec5SDimitry Andric break; 36080b57cec5SDimitry Andric ++__first; 36090b57cec5SDimitry Andric } 36100b57cec5SDimitry Andric // We now have a reduced range [__first, __last) 36110b57cec5SDimitry Andric // *__first is known to be false 36120b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator>::difference_type difference_type; 36130b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator>::value_type value_type; 36140b57cec5SDimitry Andric difference_type __len = _VSTD::distance(__first, __last); 36150b57cec5SDimitry Andric pair<value_type*, ptrdiff_t> __p(0, 0); 36160b57cec5SDimitry Andric unique_ptr<value_type, __return_temporary_buffer> __h; 36170b57cec5SDimitry Andric if (__len >= __alloc_limit) 36180b57cec5SDimitry Andric { 36190b57cec5SDimitry Andric __p = _VSTD::get_temporary_buffer<value_type>(__len); 36200b57cec5SDimitry Andric __h.reset(__p.first); 36210b57cec5SDimitry Andric } 3622*e8d8bef9SDimitry Andric return _VSTD::__stable_partition<typename add_lvalue_reference<_Predicate>::type> 36230b57cec5SDimitry Andric (__first, __last, __pred, __len, __p, forward_iterator_tag()); 36240b57cec5SDimitry Andric} 36250b57cec5SDimitry Andric 36260b57cec5SDimitry Andrictemplate <class _Predicate, class _BidirectionalIterator, class _Distance, class _Pair> 36270b57cec5SDimitry Andric_BidirectionalIterator 36280b57cec5SDimitry Andric__stable_partition(_BidirectionalIterator __first, _BidirectionalIterator __last, _Predicate __pred, 36290b57cec5SDimitry Andric _Distance __len, _Pair __p, bidirectional_iterator_tag __bit) 36300b57cec5SDimitry Andric{ 36310b57cec5SDimitry Andric // *__first is known to be false 36320b57cec5SDimitry Andric // *__last is known to be true 36330b57cec5SDimitry Andric // __len >= 2 36340b57cec5SDimitry Andric if (__len == 2) 36350b57cec5SDimitry Andric { 36360b57cec5SDimitry Andric swap(*__first, *__last); 36370b57cec5SDimitry Andric return __last; 36380b57cec5SDimitry Andric } 36390b57cec5SDimitry Andric if (__len == 3) 36400b57cec5SDimitry Andric { 36410b57cec5SDimitry Andric _BidirectionalIterator __m = __first; 36420b57cec5SDimitry Andric if (__pred(*++__m)) 36430b57cec5SDimitry Andric { 36440b57cec5SDimitry Andric swap(*__first, *__m); 36450b57cec5SDimitry Andric swap(*__m, *__last); 36460b57cec5SDimitry Andric return __last; 36470b57cec5SDimitry Andric } 36480b57cec5SDimitry Andric swap(*__m, *__last); 36490b57cec5SDimitry Andric swap(*__first, *__m); 36500b57cec5SDimitry Andric return __m; 36510b57cec5SDimitry Andric } 36520b57cec5SDimitry Andric if (__len <= __p.second) 36530b57cec5SDimitry Andric { // The buffer is big enough to use 36540b57cec5SDimitry Andric typedef typename iterator_traits<_BidirectionalIterator>::value_type value_type; 36550b57cec5SDimitry Andric __destruct_n __d(0); 36560b57cec5SDimitry Andric unique_ptr<value_type, __destruct_n&> __h(__p.first, __d); 36570b57cec5SDimitry Andric // Move the falses into the temporary buffer, and the trues to the front of the line 36580b57cec5SDimitry Andric // Update __first to always point to the end of the trues 36590b57cec5SDimitry Andric value_type* __t = __p.first; 3660*e8d8bef9SDimitry Andric ::new ((void*)__t) value_type(_VSTD::move(*__first)); 3661*e8d8bef9SDimitry Andric __d.template __incr<value_type>(); 36620b57cec5SDimitry Andric ++__t; 36630b57cec5SDimitry Andric _BidirectionalIterator __i = __first; 36640b57cec5SDimitry Andric while (++__i != __last) 36650b57cec5SDimitry Andric { 36660b57cec5SDimitry Andric if (__pred(*__i)) 36670b57cec5SDimitry Andric { 36680b57cec5SDimitry Andric *__first = _VSTD::move(*__i); 36690b57cec5SDimitry Andric ++__first; 36700b57cec5SDimitry Andric } 36710b57cec5SDimitry Andric else 36720b57cec5SDimitry Andric { 3673*e8d8bef9SDimitry Andric ::new ((void*)__t) value_type(_VSTD::move(*__i)); 3674*e8d8bef9SDimitry Andric __d.template __incr<value_type>(); 36750b57cec5SDimitry Andric ++__t; 36760b57cec5SDimitry Andric } 36770b57cec5SDimitry Andric } 36780b57cec5SDimitry Andric // move *__last, known to be true 36790b57cec5SDimitry Andric *__first = _VSTD::move(*__i); 36800b57cec5SDimitry Andric __i = ++__first; 36810b57cec5SDimitry Andric // All trues now at start of range, all falses in buffer 36820b57cec5SDimitry Andric // Move falses back into range, but don't mess up __first which points to first false 3683e40139ffSDimitry Andric for (value_type* __t2 = __p.first; __t2 < __t; ++__t2, (void) ++__i) 36840b57cec5SDimitry Andric *__i = _VSTD::move(*__t2); 36850b57cec5SDimitry Andric // __h destructs moved-from values out of the temp buffer, but doesn't deallocate buffer 36860b57cec5SDimitry Andric return __first; 36870b57cec5SDimitry Andric } 36880b57cec5SDimitry Andric // Else not enough buffer, do in place 36890b57cec5SDimitry Andric // __len >= 4 36900b57cec5SDimitry Andric _BidirectionalIterator __m = __first; 36910b57cec5SDimitry Andric _Distance __len2 = __len / 2; // __len2 >= 2 36920b57cec5SDimitry Andric _VSTD::advance(__m, __len2); 36930b57cec5SDimitry Andric // recurse on [__first, __m-1], except reduce __m-1 until *(__m-1) is true, *__first know to be false 36940b57cec5SDimitry Andric // F????????????????T 36950b57cec5SDimitry Andric // f m l 36960b57cec5SDimitry Andric _BidirectionalIterator __m1 = __m; 36970b57cec5SDimitry Andric _BidirectionalIterator __first_false = __first; 36980b57cec5SDimitry Andric _Distance __len_half = __len2; 36990b57cec5SDimitry Andric while (!__pred(*--__m1)) 37000b57cec5SDimitry Andric { 37010b57cec5SDimitry Andric if (__m1 == __first) 37020b57cec5SDimitry Andric goto __first_half_done; 37030b57cec5SDimitry Andric --__len_half; 37040b57cec5SDimitry Andric } 37050b57cec5SDimitry Andric // F???TFFF?????????T 37060b57cec5SDimitry Andric // f m1 m l 37070b57cec5SDimitry Andric typedef typename add_lvalue_reference<_Predicate>::type _PredRef; 3708*e8d8bef9SDimitry Andric __first_false = _VSTD::__stable_partition<_PredRef>(__first, __m1, __pred, __len_half, __p, __bit); 37090b57cec5SDimitry Andric__first_half_done: 37100b57cec5SDimitry Andric // TTTFFFFF?????????T 37110b57cec5SDimitry Andric // f ff m l 37120b57cec5SDimitry Andric // recurse on [__m, __last], except increase __m until *(__m) is false, *__last know to be true 37130b57cec5SDimitry Andric __m1 = __m; 37140b57cec5SDimitry Andric _BidirectionalIterator __second_false = __last; 37150b57cec5SDimitry Andric ++__second_false; 37160b57cec5SDimitry Andric __len_half = __len - __len2; 37170b57cec5SDimitry Andric while (__pred(*__m1)) 37180b57cec5SDimitry Andric { 37190b57cec5SDimitry Andric if (++__m1 == __last) 37200b57cec5SDimitry Andric goto __second_half_done; 37210b57cec5SDimitry Andric --__len_half; 37220b57cec5SDimitry Andric } 37230b57cec5SDimitry Andric // TTTFFFFFTTTF?????T 37240b57cec5SDimitry Andric // f ff m m1 l 3725*e8d8bef9SDimitry Andric __second_false = _VSTD::__stable_partition<_PredRef>(__m1, __last, __pred, __len_half, __p, __bit); 37260b57cec5SDimitry Andric__second_half_done: 37270b57cec5SDimitry Andric // TTTFFFFFTTTTTFFFFF 37280b57cec5SDimitry Andric // f ff m sf l 37290b57cec5SDimitry Andric return _VSTD::rotate(__first_false, __m, __second_false); 37300b57cec5SDimitry Andric // TTTTTTTTFFFFFFFFFF 37310b57cec5SDimitry Andric // | 37320b57cec5SDimitry Andric} 37330b57cec5SDimitry Andric 37340b57cec5SDimitry Andrictemplate <class _Predicate, class _BidirectionalIterator> 37350b57cec5SDimitry Andric_BidirectionalIterator 37360b57cec5SDimitry Andric__stable_partition(_BidirectionalIterator __first, _BidirectionalIterator __last, _Predicate __pred, 37370b57cec5SDimitry Andric bidirectional_iterator_tag) 37380b57cec5SDimitry Andric{ 37390b57cec5SDimitry Andric typedef typename iterator_traits<_BidirectionalIterator>::difference_type difference_type; 37400b57cec5SDimitry Andric typedef typename iterator_traits<_BidirectionalIterator>::value_type value_type; 37410b57cec5SDimitry Andric const difference_type __alloc_limit = 4; // might want to make this a function of trivial assignment 37420b57cec5SDimitry Andric // Either prove all true and return __first or point to first false 37430b57cec5SDimitry Andric while (true) 37440b57cec5SDimitry Andric { 37450b57cec5SDimitry Andric if (__first == __last) 37460b57cec5SDimitry Andric return __first; 37470b57cec5SDimitry Andric if (!__pred(*__first)) 37480b57cec5SDimitry Andric break; 37490b57cec5SDimitry Andric ++__first; 37500b57cec5SDimitry Andric } 37510b57cec5SDimitry Andric // __first points to first false, everything prior to __first is already set. 37520b57cec5SDimitry Andric // Either prove [__first, __last) is all false and return __first, or point __last to last true 37530b57cec5SDimitry Andric do 37540b57cec5SDimitry Andric { 37550b57cec5SDimitry Andric if (__first == --__last) 37560b57cec5SDimitry Andric return __first; 37570b57cec5SDimitry Andric } while (!__pred(*__last)); 37580b57cec5SDimitry Andric // We now have a reduced range [__first, __last] 37590b57cec5SDimitry Andric // *__first is known to be false 37600b57cec5SDimitry Andric // *__last is known to be true 37610b57cec5SDimitry Andric // __len >= 2 37620b57cec5SDimitry Andric difference_type __len = _VSTD::distance(__first, __last) + 1; 37630b57cec5SDimitry Andric pair<value_type*, ptrdiff_t> __p(0, 0); 37640b57cec5SDimitry Andric unique_ptr<value_type, __return_temporary_buffer> __h; 37650b57cec5SDimitry Andric if (__len >= __alloc_limit) 37660b57cec5SDimitry Andric { 37670b57cec5SDimitry Andric __p = _VSTD::get_temporary_buffer<value_type>(__len); 37680b57cec5SDimitry Andric __h.reset(__p.first); 37690b57cec5SDimitry Andric } 3770*e8d8bef9SDimitry Andric return _VSTD::__stable_partition<typename add_lvalue_reference<_Predicate>::type> 37710b57cec5SDimitry Andric (__first, __last, __pred, __len, __p, bidirectional_iterator_tag()); 37720b57cec5SDimitry Andric} 37730b57cec5SDimitry Andric 37740b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Predicate> 37750b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 37760b57cec5SDimitry Andric_ForwardIterator 37770b57cec5SDimitry Andricstable_partition(_ForwardIterator __first, _ForwardIterator __last, _Predicate __pred) 37780b57cec5SDimitry Andric{ 3779*e8d8bef9SDimitry Andric return _VSTD::__stable_partition<typename add_lvalue_reference<_Predicate>::type> 37800b57cec5SDimitry Andric (__first, __last, __pred, typename iterator_traits<_ForwardIterator>::iterator_category()); 37810b57cec5SDimitry Andric} 37820b57cec5SDimitry Andric 37830b57cec5SDimitry Andric// is_sorted_until 37840b57cec5SDimitry Andric 37850b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Compare> 37860b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT _LIBCPP_CONSTEXPR_AFTER_CXX17 _ForwardIterator 37870b57cec5SDimitry Andricis_sorted_until(_ForwardIterator __first, _ForwardIterator __last, _Compare __comp) 37880b57cec5SDimitry Andric{ 37890b57cec5SDimitry Andric if (__first != __last) 37900b57cec5SDimitry Andric { 37910b57cec5SDimitry Andric _ForwardIterator __i = __first; 37920b57cec5SDimitry Andric while (++__i != __last) 37930b57cec5SDimitry Andric { 37940b57cec5SDimitry Andric if (__comp(*__i, *__first)) 37950b57cec5SDimitry Andric return __i; 37960b57cec5SDimitry Andric __first = __i; 37970b57cec5SDimitry Andric } 37980b57cec5SDimitry Andric } 37990b57cec5SDimitry Andric return __last; 38000b57cec5SDimitry Andric} 38010b57cec5SDimitry Andric 38020b57cec5SDimitry Andrictemplate<class _ForwardIterator> 38030b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 38040b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 38050b57cec5SDimitry Andric_ForwardIterator 38060b57cec5SDimitry Andricis_sorted_until(_ForwardIterator __first, _ForwardIterator __last) 38070b57cec5SDimitry Andric{ 38080b57cec5SDimitry Andric return _VSTD::is_sorted_until(__first, __last, __less<typename iterator_traits<_ForwardIterator>::value_type>()); 38090b57cec5SDimitry Andric} 38100b57cec5SDimitry Andric 38110b57cec5SDimitry Andric// is_sorted 38120b57cec5SDimitry Andric 38130b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Compare> 38140b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 38150b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 38160b57cec5SDimitry Andricbool 38170b57cec5SDimitry Andricis_sorted(_ForwardIterator __first, _ForwardIterator __last, _Compare __comp) 38180b57cec5SDimitry Andric{ 38190b57cec5SDimitry Andric return _VSTD::is_sorted_until(__first, __last, __comp) == __last; 38200b57cec5SDimitry Andric} 38210b57cec5SDimitry Andric 38220b57cec5SDimitry Andrictemplate<class _ForwardIterator> 38230b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 38240b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 38250b57cec5SDimitry Andricbool 38260b57cec5SDimitry Andricis_sorted(_ForwardIterator __first, _ForwardIterator __last) 38270b57cec5SDimitry Andric{ 38280b57cec5SDimitry Andric return _VSTD::is_sorted(__first, __last, __less<typename iterator_traits<_ForwardIterator>::value_type>()); 38290b57cec5SDimitry Andric} 38300b57cec5SDimitry Andric 38310b57cec5SDimitry Andric// sort 38320b57cec5SDimitry Andric 38330b57cec5SDimitry Andric// stable, 2-3 compares, 0-2 swaps 38340b57cec5SDimitry Andric 38350b57cec5SDimitry Andrictemplate <class _Compare, class _ForwardIterator> 38360b57cec5SDimitry Andricunsigned 38370b57cec5SDimitry Andric__sort3(_ForwardIterator __x, _ForwardIterator __y, _ForwardIterator __z, _Compare __c) 38380b57cec5SDimitry Andric{ 38390b57cec5SDimitry Andric unsigned __r = 0; 38400b57cec5SDimitry Andric if (!__c(*__y, *__x)) // if x <= y 38410b57cec5SDimitry Andric { 38420b57cec5SDimitry Andric if (!__c(*__z, *__y)) // if y <= z 38430b57cec5SDimitry Andric return __r; // x <= y && y <= z 38440b57cec5SDimitry Andric // x <= y && y > z 38450b57cec5SDimitry Andric swap(*__y, *__z); // x <= z && y < z 38460b57cec5SDimitry Andric __r = 1; 38470b57cec5SDimitry Andric if (__c(*__y, *__x)) // if x > y 38480b57cec5SDimitry Andric { 38490b57cec5SDimitry Andric swap(*__x, *__y); // x < y && y <= z 38500b57cec5SDimitry Andric __r = 2; 38510b57cec5SDimitry Andric } 38520b57cec5SDimitry Andric return __r; // x <= y && y < z 38530b57cec5SDimitry Andric } 38540b57cec5SDimitry Andric if (__c(*__z, *__y)) // x > y, if y > z 38550b57cec5SDimitry Andric { 38560b57cec5SDimitry Andric swap(*__x, *__z); // x < y && y < z 38570b57cec5SDimitry Andric __r = 1; 38580b57cec5SDimitry Andric return __r; 38590b57cec5SDimitry Andric } 38600b57cec5SDimitry Andric swap(*__x, *__y); // x > y && y <= z 38610b57cec5SDimitry Andric __r = 1; // x < y && x <= z 38620b57cec5SDimitry Andric if (__c(*__z, *__y)) // if y > z 38630b57cec5SDimitry Andric { 38640b57cec5SDimitry Andric swap(*__y, *__z); // x <= y && y < z 38650b57cec5SDimitry Andric __r = 2; 38660b57cec5SDimitry Andric } 38670b57cec5SDimitry Andric return __r; 38680b57cec5SDimitry Andric} // x <= y && y <= z 38690b57cec5SDimitry Andric 38700b57cec5SDimitry Andric// stable, 3-6 compares, 0-5 swaps 38710b57cec5SDimitry Andric 38720b57cec5SDimitry Andrictemplate <class _Compare, class _ForwardIterator> 38730b57cec5SDimitry Andricunsigned 38740b57cec5SDimitry Andric__sort4(_ForwardIterator __x1, _ForwardIterator __x2, _ForwardIterator __x3, 38750b57cec5SDimitry Andric _ForwardIterator __x4, _Compare __c) 38760b57cec5SDimitry Andric{ 3877*e8d8bef9SDimitry Andric unsigned __r = _VSTD::__sort3<_Compare>(__x1, __x2, __x3, __c); 38780b57cec5SDimitry Andric if (__c(*__x4, *__x3)) 38790b57cec5SDimitry Andric { 38800b57cec5SDimitry Andric swap(*__x3, *__x4); 38810b57cec5SDimitry Andric ++__r; 38820b57cec5SDimitry Andric if (__c(*__x3, *__x2)) 38830b57cec5SDimitry Andric { 38840b57cec5SDimitry Andric swap(*__x2, *__x3); 38850b57cec5SDimitry Andric ++__r; 38860b57cec5SDimitry Andric if (__c(*__x2, *__x1)) 38870b57cec5SDimitry Andric { 38880b57cec5SDimitry Andric swap(*__x1, *__x2); 38890b57cec5SDimitry Andric ++__r; 38900b57cec5SDimitry Andric } 38910b57cec5SDimitry Andric } 38920b57cec5SDimitry Andric } 38930b57cec5SDimitry Andric return __r; 38940b57cec5SDimitry Andric} 38950b57cec5SDimitry Andric 38960b57cec5SDimitry Andric// stable, 4-10 compares, 0-9 swaps 38970b57cec5SDimitry Andric 38980b57cec5SDimitry Andrictemplate <class _Compare, class _ForwardIterator> 38990b57cec5SDimitry Andric_LIBCPP_HIDDEN 39000b57cec5SDimitry Andricunsigned 39010b57cec5SDimitry Andric__sort5(_ForwardIterator __x1, _ForwardIterator __x2, _ForwardIterator __x3, 39020b57cec5SDimitry Andric _ForwardIterator __x4, _ForwardIterator __x5, _Compare __c) 39030b57cec5SDimitry Andric{ 3904*e8d8bef9SDimitry Andric unsigned __r = _VSTD::__sort4<_Compare>(__x1, __x2, __x3, __x4, __c); 39050b57cec5SDimitry Andric if (__c(*__x5, *__x4)) 39060b57cec5SDimitry Andric { 39070b57cec5SDimitry Andric swap(*__x4, *__x5); 39080b57cec5SDimitry Andric ++__r; 39090b57cec5SDimitry Andric if (__c(*__x4, *__x3)) 39100b57cec5SDimitry Andric { 39110b57cec5SDimitry Andric swap(*__x3, *__x4); 39120b57cec5SDimitry Andric ++__r; 39130b57cec5SDimitry Andric if (__c(*__x3, *__x2)) 39140b57cec5SDimitry Andric { 39150b57cec5SDimitry Andric swap(*__x2, *__x3); 39160b57cec5SDimitry Andric ++__r; 39170b57cec5SDimitry Andric if (__c(*__x2, *__x1)) 39180b57cec5SDimitry Andric { 39190b57cec5SDimitry Andric swap(*__x1, *__x2); 39200b57cec5SDimitry Andric ++__r; 39210b57cec5SDimitry Andric } 39220b57cec5SDimitry Andric } 39230b57cec5SDimitry Andric } 39240b57cec5SDimitry Andric } 39250b57cec5SDimitry Andric return __r; 39260b57cec5SDimitry Andric} 39270b57cec5SDimitry Andric 39280b57cec5SDimitry Andric// Assumes size > 0 3929*e8d8bef9SDimitry Andrictemplate <class _Compare, class _BidirectionalIterator> 39300b57cec5SDimitry Andricvoid 3931*e8d8bef9SDimitry Andric__selection_sort(_BidirectionalIterator __first, _BidirectionalIterator __last, _Compare __comp) 39320b57cec5SDimitry Andric{ 3933*e8d8bef9SDimitry Andric _BidirectionalIterator __lm1 = __last; 39340b57cec5SDimitry Andric for (--__lm1; __first != __lm1; ++__first) 39350b57cec5SDimitry Andric { 3936*e8d8bef9SDimitry Andric _BidirectionalIterator __i = _VSTD::min_element<_BidirectionalIterator, 39370b57cec5SDimitry Andric typename add_lvalue_reference<_Compare>::type> 39380b57cec5SDimitry Andric (__first, __last, __comp); 39390b57cec5SDimitry Andric if (__i != __first) 39400b57cec5SDimitry Andric swap(*__first, *__i); 39410b57cec5SDimitry Andric } 39420b57cec5SDimitry Andric} 39430b57cec5SDimitry Andric 3944*e8d8bef9SDimitry Andrictemplate <class _Compare, class _BidirectionalIterator> 39450b57cec5SDimitry Andricvoid 3946*e8d8bef9SDimitry Andric__insertion_sort(_BidirectionalIterator __first, _BidirectionalIterator __last, _Compare __comp) 39470b57cec5SDimitry Andric{ 3948*e8d8bef9SDimitry Andric typedef typename iterator_traits<_BidirectionalIterator>::value_type value_type; 39490b57cec5SDimitry Andric if (__first != __last) 39500b57cec5SDimitry Andric { 3951*e8d8bef9SDimitry Andric _BidirectionalIterator __i = __first; 39520b57cec5SDimitry Andric for (++__i; __i != __last; ++__i) 39530b57cec5SDimitry Andric { 3954*e8d8bef9SDimitry Andric _BidirectionalIterator __j = __i; 39550b57cec5SDimitry Andric value_type __t(_VSTD::move(*__j)); 3956*e8d8bef9SDimitry Andric for (_BidirectionalIterator __k = __i; __k != __first && __comp(__t, *--__k); --__j) 39570b57cec5SDimitry Andric *__j = _VSTD::move(*__k); 39580b57cec5SDimitry Andric *__j = _VSTD::move(__t); 39590b57cec5SDimitry Andric } 39600b57cec5SDimitry Andric } 39610b57cec5SDimitry Andric} 39620b57cec5SDimitry Andric 39630b57cec5SDimitry Andrictemplate <class _Compare, class _RandomAccessIterator> 39640b57cec5SDimitry Andricvoid 39650b57cec5SDimitry Andric__insertion_sort_3(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) 39660b57cec5SDimitry Andric{ 39670b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::value_type value_type; 39680b57cec5SDimitry Andric _RandomAccessIterator __j = __first+2; 3969*e8d8bef9SDimitry Andric _VSTD::__sort3<_Compare>(__first, __first+1, __j, __comp); 39700b57cec5SDimitry Andric for (_RandomAccessIterator __i = __j+1; __i != __last; ++__i) 39710b57cec5SDimitry Andric { 39720b57cec5SDimitry Andric if (__comp(*__i, *__j)) 39730b57cec5SDimitry Andric { 39740b57cec5SDimitry Andric value_type __t(_VSTD::move(*__i)); 39750b57cec5SDimitry Andric _RandomAccessIterator __k = __j; 39760b57cec5SDimitry Andric __j = __i; 39770b57cec5SDimitry Andric do 39780b57cec5SDimitry Andric { 39790b57cec5SDimitry Andric *__j = _VSTD::move(*__k); 39800b57cec5SDimitry Andric __j = __k; 39810b57cec5SDimitry Andric } while (__j != __first && __comp(__t, *--__k)); 39820b57cec5SDimitry Andric *__j = _VSTD::move(__t); 39830b57cec5SDimitry Andric } 39840b57cec5SDimitry Andric __j = __i; 39850b57cec5SDimitry Andric } 39860b57cec5SDimitry Andric} 39870b57cec5SDimitry Andric 39880b57cec5SDimitry Andrictemplate <class _Compare, class _RandomAccessIterator> 39890b57cec5SDimitry Andricbool 39900b57cec5SDimitry Andric__insertion_sort_incomplete(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) 39910b57cec5SDimitry Andric{ 39920b57cec5SDimitry Andric switch (__last - __first) 39930b57cec5SDimitry Andric { 39940b57cec5SDimitry Andric case 0: 39950b57cec5SDimitry Andric case 1: 39960b57cec5SDimitry Andric return true; 39970b57cec5SDimitry Andric case 2: 39980b57cec5SDimitry Andric if (__comp(*--__last, *__first)) 39990b57cec5SDimitry Andric swap(*__first, *__last); 40000b57cec5SDimitry Andric return true; 40010b57cec5SDimitry Andric case 3: 40020b57cec5SDimitry Andric _VSTD::__sort3<_Compare>(__first, __first+1, --__last, __comp); 40030b57cec5SDimitry Andric return true; 40040b57cec5SDimitry Andric case 4: 40050b57cec5SDimitry Andric _VSTD::__sort4<_Compare>(__first, __first+1, __first+2, --__last, __comp); 40060b57cec5SDimitry Andric return true; 40070b57cec5SDimitry Andric case 5: 40080b57cec5SDimitry Andric _VSTD::__sort5<_Compare>(__first, __first+1, __first+2, __first+3, --__last, __comp); 40090b57cec5SDimitry Andric return true; 40100b57cec5SDimitry Andric } 40110b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::value_type value_type; 40120b57cec5SDimitry Andric _RandomAccessIterator __j = __first+2; 4013*e8d8bef9SDimitry Andric _VSTD::__sort3<_Compare>(__first, __first+1, __j, __comp); 40140b57cec5SDimitry Andric const unsigned __limit = 8; 40150b57cec5SDimitry Andric unsigned __count = 0; 40160b57cec5SDimitry Andric for (_RandomAccessIterator __i = __j+1; __i != __last; ++__i) 40170b57cec5SDimitry Andric { 40180b57cec5SDimitry Andric if (__comp(*__i, *__j)) 40190b57cec5SDimitry Andric { 40200b57cec5SDimitry Andric value_type __t(_VSTD::move(*__i)); 40210b57cec5SDimitry Andric _RandomAccessIterator __k = __j; 40220b57cec5SDimitry Andric __j = __i; 40230b57cec5SDimitry Andric do 40240b57cec5SDimitry Andric { 40250b57cec5SDimitry Andric *__j = _VSTD::move(*__k); 40260b57cec5SDimitry Andric __j = __k; 40270b57cec5SDimitry Andric } while (__j != __first && __comp(__t, *--__k)); 40280b57cec5SDimitry Andric *__j = _VSTD::move(__t); 40290b57cec5SDimitry Andric if (++__count == __limit) 40300b57cec5SDimitry Andric return ++__i == __last; 40310b57cec5SDimitry Andric } 40320b57cec5SDimitry Andric __j = __i; 40330b57cec5SDimitry Andric } 40340b57cec5SDimitry Andric return true; 40350b57cec5SDimitry Andric} 40360b57cec5SDimitry Andric 4037*e8d8bef9SDimitry Andrictemplate <class _Compare, class _BidirectionalIterator> 40380b57cec5SDimitry Andricvoid 4039*e8d8bef9SDimitry Andric__insertion_sort_move(_BidirectionalIterator __first1, _BidirectionalIterator __last1, 4040*e8d8bef9SDimitry Andric typename iterator_traits<_BidirectionalIterator>::value_type* __first2, _Compare __comp) 40410b57cec5SDimitry Andric{ 4042*e8d8bef9SDimitry Andric typedef typename iterator_traits<_BidirectionalIterator>::value_type value_type; 40430b57cec5SDimitry Andric if (__first1 != __last1) 40440b57cec5SDimitry Andric { 40450b57cec5SDimitry Andric __destruct_n __d(0); 40460b57cec5SDimitry Andric unique_ptr<value_type, __destruct_n&> __h(__first2, __d); 40470b57cec5SDimitry Andric value_type* __last2 = __first2; 4048*e8d8bef9SDimitry Andric ::new ((void*)__last2) value_type(_VSTD::move(*__first1)); 4049*e8d8bef9SDimitry Andric __d.template __incr<value_type>(); 40500b57cec5SDimitry Andric for (++__last2; ++__first1 != __last1; ++__last2) 40510b57cec5SDimitry Andric { 40520b57cec5SDimitry Andric value_type* __j2 = __last2; 40530b57cec5SDimitry Andric value_type* __i2 = __j2; 40540b57cec5SDimitry Andric if (__comp(*__first1, *--__i2)) 40550b57cec5SDimitry Andric { 4056*e8d8bef9SDimitry Andric ::new ((void*)__j2) value_type(_VSTD::move(*__i2)); 4057*e8d8bef9SDimitry Andric __d.template __incr<value_type>(); 40580b57cec5SDimitry Andric for (--__j2; __i2 != __first2 && __comp(*__first1, *--__i2); --__j2) 40590b57cec5SDimitry Andric *__j2 = _VSTD::move(*__i2); 40600b57cec5SDimitry Andric *__j2 = _VSTD::move(*__first1); 40610b57cec5SDimitry Andric } 40620b57cec5SDimitry Andric else 40630b57cec5SDimitry Andric { 4064*e8d8bef9SDimitry Andric ::new ((void*)__j2) value_type(_VSTD::move(*__first1)); 4065*e8d8bef9SDimitry Andric __d.template __incr<value_type>(); 40660b57cec5SDimitry Andric } 40670b57cec5SDimitry Andric } 40680b57cec5SDimitry Andric __h.release(); 40690b57cec5SDimitry Andric } 40700b57cec5SDimitry Andric} 40710b57cec5SDimitry Andric 40720b57cec5SDimitry Andrictemplate <class _Compare, class _RandomAccessIterator> 40730b57cec5SDimitry Andricvoid 40740b57cec5SDimitry Andric__sort(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) 40750b57cec5SDimitry Andric{ 40760b57cec5SDimitry Andric // _Compare is known to be a reference type 40770b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::difference_type difference_type; 40780b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::value_type value_type; 40790b57cec5SDimitry Andric const difference_type __limit = is_trivially_copy_constructible<value_type>::value && 40800b57cec5SDimitry Andric is_trivially_copy_assignable<value_type>::value ? 30 : 6; 40810b57cec5SDimitry Andric while (true) 40820b57cec5SDimitry Andric { 40830b57cec5SDimitry Andric __restart: 40840b57cec5SDimitry Andric difference_type __len = __last - __first; 40850b57cec5SDimitry Andric switch (__len) 40860b57cec5SDimitry Andric { 40870b57cec5SDimitry Andric case 0: 40880b57cec5SDimitry Andric case 1: 40890b57cec5SDimitry Andric return; 40900b57cec5SDimitry Andric case 2: 40910b57cec5SDimitry Andric if (__comp(*--__last, *__first)) 40920b57cec5SDimitry Andric swap(*__first, *__last); 40930b57cec5SDimitry Andric return; 40940b57cec5SDimitry Andric case 3: 40950b57cec5SDimitry Andric _VSTD::__sort3<_Compare>(__first, __first+1, --__last, __comp); 40960b57cec5SDimitry Andric return; 40970b57cec5SDimitry Andric case 4: 40980b57cec5SDimitry Andric _VSTD::__sort4<_Compare>(__first, __first+1, __first+2, --__last, __comp); 40990b57cec5SDimitry Andric return; 41000b57cec5SDimitry Andric case 5: 41010b57cec5SDimitry Andric _VSTD::__sort5<_Compare>(__first, __first+1, __first+2, __first+3, --__last, __comp); 41020b57cec5SDimitry Andric return; 41030b57cec5SDimitry Andric } 41040b57cec5SDimitry Andric if (__len <= __limit) 41050b57cec5SDimitry Andric { 41060b57cec5SDimitry Andric _VSTD::__insertion_sort_3<_Compare>(__first, __last, __comp); 41070b57cec5SDimitry Andric return; 41080b57cec5SDimitry Andric } 41090b57cec5SDimitry Andric // __len > 5 41100b57cec5SDimitry Andric _RandomAccessIterator __m = __first; 41110b57cec5SDimitry Andric _RandomAccessIterator __lm1 = __last; 41120b57cec5SDimitry Andric --__lm1; 41130b57cec5SDimitry Andric unsigned __n_swaps; 41140b57cec5SDimitry Andric { 41150b57cec5SDimitry Andric difference_type __delta; 41160b57cec5SDimitry Andric if (__len >= 1000) 41170b57cec5SDimitry Andric { 41180b57cec5SDimitry Andric __delta = __len/2; 41190b57cec5SDimitry Andric __m += __delta; 41200b57cec5SDimitry Andric __delta /= 2; 41210b57cec5SDimitry Andric __n_swaps = _VSTD::__sort5<_Compare>(__first, __first + __delta, __m, __m+__delta, __lm1, __comp); 41220b57cec5SDimitry Andric } 41230b57cec5SDimitry Andric else 41240b57cec5SDimitry Andric { 41250b57cec5SDimitry Andric __delta = __len/2; 41260b57cec5SDimitry Andric __m += __delta; 41270b57cec5SDimitry Andric __n_swaps = _VSTD::__sort3<_Compare>(__first, __m, __lm1, __comp); 41280b57cec5SDimitry Andric } 41290b57cec5SDimitry Andric } 41300b57cec5SDimitry Andric // *__m is median 41310b57cec5SDimitry Andric // partition [__first, __m) < *__m and *__m <= [__m, __last) 41320b57cec5SDimitry Andric // (this inhibits tossing elements equivalent to __m around unnecessarily) 41330b57cec5SDimitry Andric _RandomAccessIterator __i = __first; 41340b57cec5SDimitry Andric _RandomAccessIterator __j = __lm1; 41350b57cec5SDimitry Andric // j points beyond range to be tested, *__m is known to be <= *__lm1 41360b57cec5SDimitry Andric // The search going up is known to be guarded but the search coming down isn't. 41370b57cec5SDimitry Andric // Prime the downward search with a guard. 41380b57cec5SDimitry Andric if (!__comp(*__i, *__m)) // if *__first == *__m 41390b57cec5SDimitry Andric { 41400b57cec5SDimitry Andric // *__first == *__m, *__first doesn't go in first part 41410b57cec5SDimitry Andric // manually guard downward moving __j against __i 41420b57cec5SDimitry Andric while (true) 41430b57cec5SDimitry Andric { 41440b57cec5SDimitry Andric if (__i == --__j) 41450b57cec5SDimitry Andric { 41460b57cec5SDimitry Andric // *__first == *__m, *__m <= all other elements 41470b57cec5SDimitry Andric // Parition instead into [__first, __i) == *__first and *__first < [__i, __last) 41480b57cec5SDimitry Andric ++__i; // __first + 1 41490b57cec5SDimitry Andric __j = __last; 41500b57cec5SDimitry Andric if (!__comp(*__first, *--__j)) // we need a guard if *__first == *(__last-1) 41510b57cec5SDimitry Andric { 41520b57cec5SDimitry Andric while (true) 41530b57cec5SDimitry Andric { 41540b57cec5SDimitry Andric if (__i == __j) 41550b57cec5SDimitry Andric return; // [__first, __last) all equivalent elements 41560b57cec5SDimitry Andric if (__comp(*__first, *__i)) 41570b57cec5SDimitry Andric { 41580b57cec5SDimitry Andric swap(*__i, *__j); 41590b57cec5SDimitry Andric ++__n_swaps; 41600b57cec5SDimitry Andric ++__i; 41610b57cec5SDimitry Andric break; 41620b57cec5SDimitry Andric } 41630b57cec5SDimitry Andric ++__i; 41640b57cec5SDimitry Andric } 41650b57cec5SDimitry Andric } 41660b57cec5SDimitry Andric // [__first, __i) == *__first and *__first < [__j, __last) and __j == __last - 1 41670b57cec5SDimitry Andric if (__i == __j) 41680b57cec5SDimitry Andric return; 41690b57cec5SDimitry Andric while (true) 41700b57cec5SDimitry Andric { 41710b57cec5SDimitry Andric while (!__comp(*__first, *__i)) 41720b57cec5SDimitry Andric ++__i; 41730b57cec5SDimitry Andric while (__comp(*__first, *--__j)) 41740b57cec5SDimitry Andric ; 41750b57cec5SDimitry Andric if (__i >= __j) 41760b57cec5SDimitry Andric break; 41770b57cec5SDimitry Andric swap(*__i, *__j); 41780b57cec5SDimitry Andric ++__n_swaps; 41790b57cec5SDimitry Andric ++__i; 41800b57cec5SDimitry Andric } 41810b57cec5SDimitry Andric // [__first, __i) == *__first and *__first < [__i, __last) 4182*e8d8bef9SDimitry Andric // The first part is sorted, sort the second part 41830b57cec5SDimitry Andric // _VSTD::__sort<_Compare>(__i, __last, __comp); 41840b57cec5SDimitry Andric __first = __i; 41850b57cec5SDimitry Andric goto __restart; 41860b57cec5SDimitry Andric } 41870b57cec5SDimitry Andric if (__comp(*__j, *__m)) 41880b57cec5SDimitry Andric { 41890b57cec5SDimitry Andric swap(*__i, *__j); 41900b57cec5SDimitry Andric ++__n_swaps; 41910b57cec5SDimitry Andric break; // found guard for downward moving __j, now use unguarded partition 41920b57cec5SDimitry Andric } 41930b57cec5SDimitry Andric } 41940b57cec5SDimitry Andric } 41950b57cec5SDimitry Andric // It is known that *__i < *__m 41960b57cec5SDimitry Andric ++__i; 41970b57cec5SDimitry Andric // j points beyond range to be tested, *__m is known to be <= *__lm1 41980b57cec5SDimitry Andric // if not yet partitioned... 41990b57cec5SDimitry Andric if (__i < __j) 42000b57cec5SDimitry Andric { 42010b57cec5SDimitry Andric // known that *(__i - 1) < *__m 42020b57cec5SDimitry Andric // known that __i <= __m 42030b57cec5SDimitry Andric while (true) 42040b57cec5SDimitry Andric { 42050b57cec5SDimitry Andric // __m still guards upward moving __i 42060b57cec5SDimitry Andric while (__comp(*__i, *__m)) 42070b57cec5SDimitry Andric ++__i; 42080b57cec5SDimitry Andric // It is now known that a guard exists for downward moving __j 42090b57cec5SDimitry Andric while (!__comp(*--__j, *__m)) 42100b57cec5SDimitry Andric ; 42110b57cec5SDimitry Andric if (__i > __j) 42120b57cec5SDimitry Andric break; 42130b57cec5SDimitry Andric swap(*__i, *__j); 42140b57cec5SDimitry Andric ++__n_swaps; 42150b57cec5SDimitry Andric // It is known that __m != __j 42160b57cec5SDimitry Andric // If __m just moved, follow it 42170b57cec5SDimitry Andric if (__m == __i) 42180b57cec5SDimitry Andric __m = __j; 42190b57cec5SDimitry Andric ++__i; 42200b57cec5SDimitry Andric } 42210b57cec5SDimitry Andric } 42220b57cec5SDimitry Andric // [__first, __i) < *__m and *__m <= [__i, __last) 42230b57cec5SDimitry Andric if (__i != __m && __comp(*__m, *__i)) 42240b57cec5SDimitry Andric { 42250b57cec5SDimitry Andric swap(*__i, *__m); 42260b57cec5SDimitry Andric ++__n_swaps; 42270b57cec5SDimitry Andric } 42280b57cec5SDimitry Andric // [__first, __i) < *__i and *__i <= [__i+1, __last) 42290b57cec5SDimitry Andric // If we were given a perfect partition, see if insertion sort is quick... 42300b57cec5SDimitry Andric if (__n_swaps == 0) 42310b57cec5SDimitry Andric { 42320b57cec5SDimitry Andric bool __fs = _VSTD::__insertion_sort_incomplete<_Compare>(__first, __i, __comp); 42330b57cec5SDimitry Andric if (_VSTD::__insertion_sort_incomplete<_Compare>(__i+1, __last, __comp)) 42340b57cec5SDimitry Andric { 42350b57cec5SDimitry Andric if (__fs) 42360b57cec5SDimitry Andric return; 42370b57cec5SDimitry Andric __last = __i; 42380b57cec5SDimitry Andric continue; 42390b57cec5SDimitry Andric } 42400b57cec5SDimitry Andric else 42410b57cec5SDimitry Andric { 42420b57cec5SDimitry Andric if (__fs) 42430b57cec5SDimitry Andric { 42440b57cec5SDimitry Andric __first = ++__i; 42450b57cec5SDimitry Andric continue; 42460b57cec5SDimitry Andric } 42470b57cec5SDimitry Andric } 42480b57cec5SDimitry Andric } 42490b57cec5SDimitry Andric // sort smaller range with recursive call and larger with tail recursion elimination 42500b57cec5SDimitry Andric if (__i - __first < __last - __i) 42510b57cec5SDimitry Andric { 42520b57cec5SDimitry Andric _VSTD::__sort<_Compare>(__first, __i, __comp); 42530b57cec5SDimitry Andric // _VSTD::__sort<_Compare>(__i+1, __last, __comp); 42540b57cec5SDimitry Andric __first = ++__i; 42550b57cec5SDimitry Andric } 42560b57cec5SDimitry Andric else 42570b57cec5SDimitry Andric { 42580b57cec5SDimitry Andric _VSTD::__sort<_Compare>(__i+1, __last, __comp); 42590b57cec5SDimitry Andric // _VSTD::__sort<_Compare>(__first, __i, __comp); 42600b57cec5SDimitry Andric __last = __i; 42610b57cec5SDimitry Andric } 42620b57cec5SDimitry Andric } 42630b57cec5SDimitry Andric} 42640b57cec5SDimitry Andric 42650b57cec5SDimitry Andric// This forwarder keeps the top call and the recursive calls using the same instantiation, forcing a reference _Compare 42660b57cec5SDimitry Andrictemplate <class _RandomAccessIterator, class _Compare> 42670b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 42680b57cec5SDimitry Andricvoid 42690b57cec5SDimitry Andricsort(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) 42700b57cec5SDimitry Andric{ 42710b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 42720b57cec5SDimitry Andric _VSTD::__sort<_Comp_ref>(__first, __last, _Comp_ref(__comp)); 42730b57cec5SDimitry Andric} 42740b57cec5SDimitry Andric 42750b57cec5SDimitry Andrictemplate <class _RandomAccessIterator> 42760b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 42770b57cec5SDimitry Andricvoid 42780b57cec5SDimitry Andricsort(_RandomAccessIterator __first, _RandomAccessIterator __last) 42790b57cec5SDimitry Andric{ 42800b57cec5SDimitry Andric _VSTD::sort(__first, __last, __less<typename iterator_traits<_RandomAccessIterator>::value_type>()); 42810b57cec5SDimitry Andric} 42820b57cec5SDimitry Andric 42830b57cec5SDimitry Andrictemplate <class _Tp> 42840b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 42850b57cec5SDimitry Andricvoid 42860b57cec5SDimitry Andricsort(_Tp** __first, _Tp** __last) 42870b57cec5SDimitry Andric{ 4288*e8d8bef9SDimitry Andric _VSTD::sort((uintptr_t*)__first, (uintptr_t*)__last, __less<uintptr_t>()); 42890b57cec5SDimitry Andric} 42900b57cec5SDimitry Andric 42910b57cec5SDimitry Andrictemplate <class _Tp> 42920b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 42930b57cec5SDimitry Andricvoid 42940b57cec5SDimitry Andricsort(__wrap_iter<_Tp*> __first, __wrap_iter<_Tp*> __last) 42950b57cec5SDimitry Andric{ 42960b57cec5SDimitry Andric _VSTD::sort(__first.base(), __last.base()); 42970b57cec5SDimitry Andric} 42980b57cec5SDimitry Andric 42990b57cec5SDimitry Andrictemplate <class _Tp, class _Compare> 43000b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 43010b57cec5SDimitry Andricvoid 43020b57cec5SDimitry Andricsort(__wrap_iter<_Tp*> __first, __wrap_iter<_Tp*> __last, _Compare __comp) 43030b57cec5SDimitry Andric{ 43040b57cec5SDimitry Andric typedef typename add_lvalue_reference<_Compare>::type _Comp_ref; 43050b57cec5SDimitry Andric _VSTD::sort<_Tp*, _Comp_ref>(__first.base(), __last.base(), __comp); 43060b57cec5SDimitry Andric} 43070b57cec5SDimitry Andric 43080b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<char>&, char*>(char*, char*, __less<char>&)) 43090b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<wchar_t>&, wchar_t*>(wchar_t*, wchar_t*, __less<wchar_t>&)) 43100b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<signed char>&, signed char*>(signed char*, signed char*, __less<signed char>&)) 43110b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<unsigned char>&, unsigned char*>(unsigned char*, unsigned char*, __less<unsigned char>&)) 43120b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<short>&, short*>(short*, short*, __less<short>&)) 43130b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<unsigned short>&, unsigned short*>(unsigned short*, unsigned short*, __less<unsigned short>&)) 43140b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<int>&, int*>(int*, int*, __less<int>&)) 43150b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<unsigned>&, unsigned*>(unsigned*, unsigned*, __less<unsigned>&)) 43160b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<long>&, long*>(long*, long*, __less<long>&)) 43170b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<unsigned long>&, unsigned long*>(unsigned long*, unsigned long*, __less<unsigned long>&)) 43180b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<long long>&, long long*>(long long*, long long*, __less<long long>&)) 43190b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<unsigned long long>&, unsigned long long*>(unsigned long long*, unsigned long long*, __less<unsigned long long>&)) 43200b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<float>&, float*>(float*, float*, __less<float>&)) 43210b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<double>&, double*>(double*, double*, __less<double>&)) 43220b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS void __sort<__less<long double>&, long double*>(long double*, long double*, __less<long double>&)) 43230b57cec5SDimitry Andric 43240b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<char>&, char*>(char*, char*, __less<char>&)) 43250b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<wchar_t>&, wchar_t*>(wchar_t*, wchar_t*, __less<wchar_t>&)) 43260b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<signed char>&, signed char*>(signed char*, signed char*, __less<signed char>&)) 43270b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<unsigned char>&, unsigned char*>(unsigned char*, unsigned char*, __less<unsigned char>&)) 43280b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<short>&, short*>(short*, short*, __less<short>&)) 43290b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<unsigned short>&, unsigned short*>(unsigned short*, unsigned short*, __less<unsigned short>&)) 43300b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<int>&, int*>(int*, int*, __less<int>&)) 43310b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<unsigned>&, unsigned*>(unsigned*, unsigned*, __less<unsigned>&)) 43320b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<long>&, long*>(long*, long*, __less<long>&)) 43330b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<unsigned long>&, unsigned long*>(unsigned long*, unsigned long*, __less<unsigned long>&)) 43340b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<long long>&, long long*>(long long*, long long*, __less<long long>&)) 43350b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<unsigned long long>&, unsigned long long*>(unsigned long long*, unsigned long long*, __less<unsigned long long>&)) 43360b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<float>&, float*>(float*, float*, __less<float>&)) 43370b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<double>&, double*>(double*, double*, __less<double>&)) 43380b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS bool __insertion_sort_incomplete<__less<long double>&, long double*>(long double*, long double*, __less<long double>&)) 43390b57cec5SDimitry Andric 43400b57cec5SDimitry Andric_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS unsigned __sort5<__less<long double>&, long double*>(long double*, long double*, long double*, long double*, long double*, __less<long double>&)) 43410b57cec5SDimitry Andric 43420b57cec5SDimitry Andric// lower_bound 43430b57cec5SDimitry Andric 43440b57cec5SDimitry Andrictemplate <class _Compare, class _ForwardIterator, class _Tp> 43450b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _ForwardIterator 43460b57cec5SDimitry Andric__lower_bound(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_, _Compare __comp) 43470b57cec5SDimitry Andric{ 43480b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator>::difference_type difference_type; 43490b57cec5SDimitry Andric difference_type __len = _VSTD::distance(__first, __last); 43500b57cec5SDimitry Andric while (__len != 0) 43510b57cec5SDimitry Andric { 43520b57cec5SDimitry Andric difference_type __l2 = _VSTD::__half_positive(__len); 43530b57cec5SDimitry Andric _ForwardIterator __m = __first; 43540b57cec5SDimitry Andric _VSTD::advance(__m, __l2); 43550b57cec5SDimitry Andric if (__comp(*__m, __value_)) 43560b57cec5SDimitry Andric { 43570b57cec5SDimitry Andric __first = ++__m; 43580b57cec5SDimitry Andric __len -= __l2 + 1; 43590b57cec5SDimitry Andric } 43600b57cec5SDimitry Andric else 43610b57cec5SDimitry Andric __len = __l2; 43620b57cec5SDimitry Andric } 43630b57cec5SDimitry Andric return __first; 43640b57cec5SDimitry Andric} 43650b57cec5SDimitry Andric 43660b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Tp, class _Compare> 43670b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 43680b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 43690b57cec5SDimitry Andric_ForwardIterator 43700b57cec5SDimitry Andriclower_bound(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_, _Compare __comp) 43710b57cec5SDimitry Andric{ 43720b57cec5SDimitry Andric typedef typename add_lvalue_reference<_Compare>::type _Comp_ref; 4373*e8d8bef9SDimitry Andric return _VSTD::__lower_bound<_Comp_ref>(__first, __last, __value_, __comp); 43740b57cec5SDimitry Andric} 43750b57cec5SDimitry Andric 43760b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Tp> 43770b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 43780b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 43790b57cec5SDimitry Andric_ForwardIterator 43800b57cec5SDimitry Andriclower_bound(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_) 43810b57cec5SDimitry Andric{ 43820b57cec5SDimitry Andric return _VSTD::lower_bound(__first, __last, __value_, 43830b57cec5SDimitry Andric __less<typename iterator_traits<_ForwardIterator>::value_type, _Tp>()); 43840b57cec5SDimitry Andric} 43850b57cec5SDimitry Andric 43860b57cec5SDimitry Andric// upper_bound 43870b57cec5SDimitry Andric 43880b57cec5SDimitry Andrictemplate <class _Compare, class _ForwardIterator, class _Tp> 43890b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _ForwardIterator 43900b57cec5SDimitry Andric__upper_bound(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_, _Compare __comp) 43910b57cec5SDimitry Andric{ 43920b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator>::difference_type difference_type; 43930b57cec5SDimitry Andric difference_type __len = _VSTD::distance(__first, __last); 43940b57cec5SDimitry Andric while (__len != 0) 43950b57cec5SDimitry Andric { 43960b57cec5SDimitry Andric difference_type __l2 = _VSTD::__half_positive(__len); 43970b57cec5SDimitry Andric _ForwardIterator __m = __first; 43980b57cec5SDimitry Andric _VSTD::advance(__m, __l2); 43990b57cec5SDimitry Andric if (__comp(__value_, *__m)) 44000b57cec5SDimitry Andric __len = __l2; 44010b57cec5SDimitry Andric else 44020b57cec5SDimitry Andric { 44030b57cec5SDimitry Andric __first = ++__m; 44040b57cec5SDimitry Andric __len -= __l2 + 1; 44050b57cec5SDimitry Andric } 44060b57cec5SDimitry Andric } 44070b57cec5SDimitry Andric return __first; 44080b57cec5SDimitry Andric} 44090b57cec5SDimitry Andric 44100b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Tp, class _Compare> 44110b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 44120b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 44130b57cec5SDimitry Andric_ForwardIterator 44140b57cec5SDimitry Andricupper_bound(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_, _Compare __comp) 44150b57cec5SDimitry Andric{ 44160b57cec5SDimitry Andric typedef typename add_lvalue_reference<_Compare>::type _Comp_ref; 4417*e8d8bef9SDimitry Andric return _VSTD::__upper_bound<_Comp_ref>(__first, __last, __value_, __comp); 44180b57cec5SDimitry Andric} 44190b57cec5SDimitry Andric 44200b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Tp> 44210b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 44220b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 44230b57cec5SDimitry Andric_ForwardIterator 44240b57cec5SDimitry Andricupper_bound(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_) 44250b57cec5SDimitry Andric{ 44260b57cec5SDimitry Andric return _VSTD::upper_bound(__first, __last, __value_, 44270b57cec5SDimitry Andric __less<_Tp, typename iterator_traits<_ForwardIterator>::value_type>()); 44280b57cec5SDimitry Andric} 44290b57cec5SDimitry Andric 44300b57cec5SDimitry Andric// equal_range 44310b57cec5SDimitry Andric 44320b57cec5SDimitry Andrictemplate <class _Compare, class _ForwardIterator, class _Tp> 44330b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 pair<_ForwardIterator, _ForwardIterator> 44340b57cec5SDimitry Andric__equal_range(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_, _Compare __comp) 44350b57cec5SDimitry Andric{ 44360b57cec5SDimitry Andric typedef typename iterator_traits<_ForwardIterator>::difference_type difference_type; 44370b57cec5SDimitry Andric difference_type __len = _VSTD::distance(__first, __last); 44380b57cec5SDimitry Andric while (__len != 0) 44390b57cec5SDimitry Andric { 44400b57cec5SDimitry Andric difference_type __l2 = _VSTD::__half_positive(__len); 44410b57cec5SDimitry Andric _ForwardIterator __m = __first; 44420b57cec5SDimitry Andric _VSTD::advance(__m, __l2); 44430b57cec5SDimitry Andric if (__comp(*__m, __value_)) 44440b57cec5SDimitry Andric { 44450b57cec5SDimitry Andric __first = ++__m; 44460b57cec5SDimitry Andric __len -= __l2 + 1; 44470b57cec5SDimitry Andric } 44480b57cec5SDimitry Andric else if (__comp(__value_, *__m)) 44490b57cec5SDimitry Andric { 44500b57cec5SDimitry Andric __last = __m; 44510b57cec5SDimitry Andric __len = __l2; 44520b57cec5SDimitry Andric } 44530b57cec5SDimitry Andric else 44540b57cec5SDimitry Andric { 44550b57cec5SDimitry Andric _ForwardIterator __mp1 = __m; 44560b57cec5SDimitry Andric return pair<_ForwardIterator, _ForwardIterator> 44570b57cec5SDimitry Andric ( 4458*e8d8bef9SDimitry Andric _VSTD::__lower_bound<_Compare>(__first, __m, __value_, __comp), 4459*e8d8bef9SDimitry Andric _VSTD::__upper_bound<_Compare>(++__mp1, __last, __value_, __comp) 44600b57cec5SDimitry Andric ); 44610b57cec5SDimitry Andric } 44620b57cec5SDimitry Andric } 44630b57cec5SDimitry Andric return pair<_ForwardIterator, _ForwardIterator>(__first, __first); 44640b57cec5SDimitry Andric} 44650b57cec5SDimitry Andric 44660b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Tp, class _Compare> 44670b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 44680b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 44690b57cec5SDimitry Andricpair<_ForwardIterator, _ForwardIterator> 44700b57cec5SDimitry Andricequal_range(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_, _Compare __comp) 44710b57cec5SDimitry Andric{ 44720b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 4473*e8d8bef9SDimitry Andric return _VSTD::__equal_range<_Comp_ref>(__first, __last, __value_, __comp); 44740b57cec5SDimitry Andric} 44750b57cec5SDimitry Andric 44760b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Tp> 44770b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 44780b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 44790b57cec5SDimitry Andricpair<_ForwardIterator, _ForwardIterator> 44800b57cec5SDimitry Andricequal_range(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_) 44810b57cec5SDimitry Andric{ 44820b57cec5SDimitry Andric return _VSTD::equal_range(__first, __last, __value_, 44830b57cec5SDimitry Andric __less<typename iterator_traits<_ForwardIterator>::value_type, _Tp>()); 44840b57cec5SDimitry Andric} 44850b57cec5SDimitry Andric 44860b57cec5SDimitry Andric// binary_search 44870b57cec5SDimitry Andric 44880b57cec5SDimitry Andrictemplate <class _Compare, class _ForwardIterator, class _Tp> 44890b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 44900b57cec5SDimitry Andricbool 44910b57cec5SDimitry Andric__binary_search(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_, _Compare __comp) 44920b57cec5SDimitry Andric{ 4493*e8d8bef9SDimitry Andric __first = _VSTD::__lower_bound<_Compare>(__first, __last, __value_, __comp); 44940b57cec5SDimitry Andric return __first != __last && !__comp(__value_, *__first); 44950b57cec5SDimitry Andric} 44960b57cec5SDimitry Andric 44970b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Tp, class _Compare> 44980b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 44990b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 45000b57cec5SDimitry Andricbool 45010b57cec5SDimitry Andricbinary_search(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_, _Compare __comp) 45020b57cec5SDimitry Andric{ 45030b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 4504*e8d8bef9SDimitry Andric return _VSTD::__binary_search<_Comp_ref>(__first, __last, __value_, __comp); 45050b57cec5SDimitry Andric} 45060b57cec5SDimitry Andric 45070b57cec5SDimitry Andrictemplate <class _ForwardIterator, class _Tp> 45080b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 45090b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 45100b57cec5SDimitry Andricbool 45110b57cec5SDimitry Andricbinary_search(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value_) 45120b57cec5SDimitry Andric{ 45130b57cec5SDimitry Andric return _VSTD::binary_search(__first, __last, __value_, 45140b57cec5SDimitry Andric __less<typename iterator_traits<_ForwardIterator>::value_type, _Tp>()); 45150b57cec5SDimitry Andric} 45160b57cec5SDimitry Andric 45170b57cec5SDimitry Andric// merge 45180b57cec5SDimitry Andric 45190b57cec5SDimitry Andrictemplate <class _Compare, class _InputIterator1, class _InputIterator2, class _OutputIterator> 4520*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 45210b57cec5SDimitry Andric_OutputIterator 45220b57cec5SDimitry Andric__merge(_InputIterator1 __first1, _InputIterator1 __last1, 45230b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result, _Compare __comp) 45240b57cec5SDimitry Andric{ 45250b57cec5SDimitry Andric for (; __first1 != __last1; ++__result) 45260b57cec5SDimitry Andric { 45270b57cec5SDimitry Andric if (__first2 == __last2) 45280b57cec5SDimitry Andric return _VSTD::copy(__first1, __last1, __result); 45290b57cec5SDimitry Andric if (__comp(*__first2, *__first1)) 45300b57cec5SDimitry Andric { 45310b57cec5SDimitry Andric *__result = *__first2; 45320b57cec5SDimitry Andric ++__first2; 45330b57cec5SDimitry Andric } 45340b57cec5SDimitry Andric else 45350b57cec5SDimitry Andric { 45360b57cec5SDimitry Andric *__result = *__first1; 45370b57cec5SDimitry Andric ++__first1; 45380b57cec5SDimitry Andric } 45390b57cec5SDimitry Andric } 45400b57cec5SDimitry Andric return _VSTD::copy(__first2, __last2, __result); 45410b57cec5SDimitry Andric} 45420b57cec5SDimitry Andric 45430b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _OutputIterator, class _Compare> 4544*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 45450b57cec5SDimitry Andric_OutputIterator 45460b57cec5SDimitry Andricmerge(_InputIterator1 __first1, _InputIterator1 __last1, 45470b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result, _Compare __comp) 45480b57cec5SDimitry Andric{ 45490b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 45500b57cec5SDimitry Andric return _VSTD::__merge<_Comp_ref>(__first1, __last1, __first2, __last2, __result, __comp); 45510b57cec5SDimitry Andric} 45520b57cec5SDimitry Andric 45530b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _OutputIterator> 4554*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 45550b57cec5SDimitry Andric_OutputIterator 45560b57cec5SDimitry Andricmerge(_InputIterator1 __first1, _InputIterator1 __last1, 45570b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result) 45580b57cec5SDimitry Andric{ 45590b57cec5SDimitry Andric typedef typename iterator_traits<_InputIterator1>::value_type __v1; 45600b57cec5SDimitry Andric typedef typename iterator_traits<_InputIterator2>::value_type __v2; 4561e40139ffSDimitry Andric return _VSTD::merge(__first1, __last1, __first2, __last2, __result, __less<__v1, __v2>()); 45620b57cec5SDimitry Andric} 45630b57cec5SDimitry Andric 45640b57cec5SDimitry Andric// inplace_merge 45650b57cec5SDimitry Andric 45660b57cec5SDimitry Andrictemplate <class _Compare, class _InputIterator1, class _InputIterator2, 45670b57cec5SDimitry Andric class _OutputIterator> 45680b57cec5SDimitry Andricvoid __half_inplace_merge(_InputIterator1 __first1, _InputIterator1 __last1, 45690b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, 45700b57cec5SDimitry Andric _OutputIterator __result, _Compare __comp) 45710b57cec5SDimitry Andric{ 45720b57cec5SDimitry Andric for (; __first1 != __last1; ++__result) 45730b57cec5SDimitry Andric { 45740b57cec5SDimitry Andric if (__first2 == __last2) 45750b57cec5SDimitry Andric { 45760b57cec5SDimitry Andric _VSTD::move(__first1, __last1, __result); 45770b57cec5SDimitry Andric return; 45780b57cec5SDimitry Andric } 45790b57cec5SDimitry Andric 45800b57cec5SDimitry Andric if (__comp(*__first2, *__first1)) 45810b57cec5SDimitry Andric { 45820b57cec5SDimitry Andric *__result = _VSTD::move(*__first2); 45830b57cec5SDimitry Andric ++__first2; 45840b57cec5SDimitry Andric } 45850b57cec5SDimitry Andric else 45860b57cec5SDimitry Andric { 45870b57cec5SDimitry Andric *__result = _VSTD::move(*__first1); 45880b57cec5SDimitry Andric ++__first1; 45890b57cec5SDimitry Andric } 45900b57cec5SDimitry Andric } 45910b57cec5SDimitry Andric // __first2 through __last2 are already in the right spot. 45920b57cec5SDimitry Andric} 45930b57cec5SDimitry Andric 45940b57cec5SDimitry Andrictemplate <class _Compare, class _BidirectionalIterator> 45950b57cec5SDimitry Andricvoid 45960b57cec5SDimitry Andric__buffered_inplace_merge(_BidirectionalIterator __first, _BidirectionalIterator __middle, _BidirectionalIterator __last, 45970b57cec5SDimitry Andric _Compare __comp, typename iterator_traits<_BidirectionalIterator>::difference_type __len1, 45980b57cec5SDimitry Andric typename iterator_traits<_BidirectionalIterator>::difference_type __len2, 45990b57cec5SDimitry Andric typename iterator_traits<_BidirectionalIterator>::value_type* __buff) 46000b57cec5SDimitry Andric{ 46010b57cec5SDimitry Andric typedef typename iterator_traits<_BidirectionalIterator>::value_type value_type; 46020b57cec5SDimitry Andric __destruct_n __d(0); 46030b57cec5SDimitry Andric unique_ptr<value_type, __destruct_n&> __h2(__buff, __d); 46040b57cec5SDimitry Andric if (__len1 <= __len2) 46050b57cec5SDimitry Andric { 46060b57cec5SDimitry Andric value_type* __p = __buff; 4607*e8d8bef9SDimitry Andric for (_BidirectionalIterator __i = __first; __i != __middle; __d.template __incr<value_type>(), (void) ++__i, (void) ++__p) 4608*e8d8bef9SDimitry Andric ::new ((void*)__p) value_type(_VSTD::move(*__i)); 4609*e8d8bef9SDimitry Andric _VSTD::__half_inplace_merge<_Compare>(__buff, __p, __middle, __last, __first, __comp); 46100b57cec5SDimitry Andric } 46110b57cec5SDimitry Andric else 46120b57cec5SDimitry Andric { 46130b57cec5SDimitry Andric value_type* __p = __buff; 4614*e8d8bef9SDimitry Andric for (_BidirectionalIterator __i = __middle; __i != __last; __d.template __incr<value_type>(), (void) ++__i, (void) ++__p) 4615*e8d8bef9SDimitry Andric ::new ((void*)__p) value_type(_VSTD::move(*__i)); 46160b57cec5SDimitry Andric typedef reverse_iterator<_BidirectionalIterator> _RBi; 46170b57cec5SDimitry Andric typedef reverse_iterator<value_type*> _Rv; 4618*e8d8bef9SDimitry Andric typedef __invert<_Compare> _Inverted; 4619*e8d8bef9SDimitry Andric _VSTD::__half_inplace_merge<_Inverted>(_Rv(__p), _Rv(__buff), 46200b57cec5SDimitry Andric _RBi(__middle), _RBi(__first), 4621*e8d8bef9SDimitry Andric _RBi(__last), _Inverted(__comp)); 46220b57cec5SDimitry Andric } 46230b57cec5SDimitry Andric} 46240b57cec5SDimitry Andric 46250b57cec5SDimitry Andrictemplate <class _Compare, class _BidirectionalIterator> 46260b57cec5SDimitry Andricvoid 46270b57cec5SDimitry Andric__inplace_merge(_BidirectionalIterator __first, _BidirectionalIterator __middle, _BidirectionalIterator __last, 46280b57cec5SDimitry Andric _Compare __comp, typename iterator_traits<_BidirectionalIterator>::difference_type __len1, 46290b57cec5SDimitry Andric typename iterator_traits<_BidirectionalIterator>::difference_type __len2, 46300b57cec5SDimitry Andric typename iterator_traits<_BidirectionalIterator>::value_type* __buff, ptrdiff_t __buff_size) 46310b57cec5SDimitry Andric{ 46320b57cec5SDimitry Andric typedef typename iterator_traits<_BidirectionalIterator>::difference_type difference_type; 46330b57cec5SDimitry Andric while (true) 46340b57cec5SDimitry Andric { 46350b57cec5SDimitry Andric // if __middle == __last, we're done 46360b57cec5SDimitry Andric if (__len2 == 0) 46370b57cec5SDimitry Andric return; 46380b57cec5SDimitry Andric if (__len1 <= __buff_size || __len2 <= __buff_size) 4639*e8d8bef9SDimitry Andric return _VSTD::__buffered_inplace_merge<_Compare> 46400b57cec5SDimitry Andric (__first, __middle, __last, __comp, __len1, __len2, __buff); 46410b57cec5SDimitry Andric // shrink [__first, __middle) as much as possible (with no moves), returning if it shrinks to 0 46420b57cec5SDimitry Andric for (; true; ++__first, (void) --__len1) 46430b57cec5SDimitry Andric { 46440b57cec5SDimitry Andric if (__len1 == 0) 46450b57cec5SDimitry Andric return; 46460b57cec5SDimitry Andric if (__comp(*__middle, *__first)) 46470b57cec5SDimitry Andric break; 46480b57cec5SDimitry Andric } 46490b57cec5SDimitry Andric // __first < __middle < __last 46500b57cec5SDimitry Andric // *__first > *__middle 46510b57cec5SDimitry Andric // partition [__first, __m1) [__m1, __middle) [__middle, __m2) [__m2, __last) such that 46520b57cec5SDimitry Andric // all elements in: 46530b57cec5SDimitry Andric // [__first, __m1) <= [__middle, __m2) 46540b57cec5SDimitry Andric // [__middle, __m2) < [__m1, __middle) 46550b57cec5SDimitry Andric // [__m1, __middle) <= [__m2, __last) 46560b57cec5SDimitry Andric // and __m1 or __m2 is in the middle of its range 46570b57cec5SDimitry Andric _BidirectionalIterator __m1; // "median" of [__first, __middle) 46580b57cec5SDimitry Andric _BidirectionalIterator __m2; // "median" of [__middle, __last) 46590b57cec5SDimitry Andric difference_type __len11; // distance(__first, __m1) 46600b57cec5SDimitry Andric difference_type __len21; // distance(__middle, __m2) 46610b57cec5SDimitry Andric // binary search smaller range 46620b57cec5SDimitry Andric if (__len1 < __len2) 46630b57cec5SDimitry Andric { // __len >= 1, __len2 >= 2 46640b57cec5SDimitry Andric __len21 = __len2 / 2; 46650b57cec5SDimitry Andric __m2 = __middle; 46660b57cec5SDimitry Andric _VSTD::advance(__m2, __len21); 4667*e8d8bef9SDimitry Andric __m1 = _VSTD::__upper_bound<_Compare>(__first, __middle, *__m2, __comp); 46680b57cec5SDimitry Andric __len11 = _VSTD::distance(__first, __m1); 46690b57cec5SDimitry Andric } 46700b57cec5SDimitry Andric else 46710b57cec5SDimitry Andric { 46720b57cec5SDimitry Andric if (__len1 == 1) 46730b57cec5SDimitry Andric { // __len1 >= __len2 && __len2 > 0, therefore __len2 == 1 46740b57cec5SDimitry Andric // It is known *__first > *__middle 46750b57cec5SDimitry Andric swap(*__first, *__middle); 46760b57cec5SDimitry Andric return; 46770b57cec5SDimitry Andric } 46780b57cec5SDimitry Andric // __len1 >= 2, __len2 >= 1 46790b57cec5SDimitry Andric __len11 = __len1 / 2; 46800b57cec5SDimitry Andric __m1 = __first; 46810b57cec5SDimitry Andric _VSTD::advance(__m1, __len11); 4682*e8d8bef9SDimitry Andric __m2 = _VSTD::__lower_bound<_Compare>(__middle, __last, *__m1, __comp); 46830b57cec5SDimitry Andric __len21 = _VSTD::distance(__middle, __m2); 46840b57cec5SDimitry Andric } 46850b57cec5SDimitry Andric difference_type __len12 = __len1 - __len11; // distance(__m1, __middle) 46860b57cec5SDimitry Andric difference_type __len22 = __len2 - __len21; // distance(__m2, __last) 46870b57cec5SDimitry Andric // [__first, __m1) [__m1, __middle) [__middle, __m2) [__m2, __last) 46880b57cec5SDimitry Andric // swap middle two partitions 46890b57cec5SDimitry Andric __middle = _VSTD::rotate(__m1, __middle, __m2); 46900b57cec5SDimitry Andric // __len12 and __len21 now have swapped meanings 4691*e8d8bef9SDimitry Andric // merge smaller range with recursive call and larger with tail recursion elimination 46920b57cec5SDimitry Andric if (__len11 + __len21 < __len12 + __len22) 46930b57cec5SDimitry Andric { 4694*e8d8bef9SDimitry Andric _VSTD::__inplace_merge<_Compare>(__first, __m1, __middle, __comp, __len11, __len21, __buff, __buff_size); 4695*e8d8bef9SDimitry Andric// _VSTD::__inplace_merge<_Compare>(__middle, __m2, __last, __comp, __len12, __len22, __buff, __buff_size); 46960b57cec5SDimitry Andric __first = __middle; 46970b57cec5SDimitry Andric __middle = __m2; 46980b57cec5SDimitry Andric __len1 = __len12; 46990b57cec5SDimitry Andric __len2 = __len22; 47000b57cec5SDimitry Andric } 47010b57cec5SDimitry Andric else 47020b57cec5SDimitry Andric { 4703*e8d8bef9SDimitry Andric _VSTD::__inplace_merge<_Compare>(__middle, __m2, __last, __comp, __len12, __len22, __buff, __buff_size); 4704*e8d8bef9SDimitry Andric// _VSTD::__inplace_merge<_Compare>(__first, __m1, __middle, __comp, __len11, __len21, __buff, __buff_size); 47050b57cec5SDimitry Andric __last = __middle; 47060b57cec5SDimitry Andric __middle = __m1; 47070b57cec5SDimitry Andric __len1 = __len11; 47080b57cec5SDimitry Andric __len2 = __len21; 47090b57cec5SDimitry Andric } 47100b57cec5SDimitry Andric } 47110b57cec5SDimitry Andric} 47120b57cec5SDimitry Andric 47130b57cec5SDimitry Andrictemplate <class _BidirectionalIterator, class _Compare> 47140b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 47150b57cec5SDimitry Andricvoid 47160b57cec5SDimitry Andricinplace_merge(_BidirectionalIterator __first, _BidirectionalIterator __middle, _BidirectionalIterator __last, 47170b57cec5SDimitry Andric _Compare __comp) 47180b57cec5SDimitry Andric{ 47190b57cec5SDimitry Andric typedef typename iterator_traits<_BidirectionalIterator>::value_type value_type; 47200b57cec5SDimitry Andric typedef typename iterator_traits<_BidirectionalIterator>::difference_type difference_type; 47210b57cec5SDimitry Andric difference_type __len1 = _VSTD::distance(__first, __middle); 47220b57cec5SDimitry Andric difference_type __len2 = _VSTD::distance(__middle, __last); 47230b57cec5SDimitry Andric difference_type __buf_size = _VSTD::min(__len1, __len2); 47240b57cec5SDimitry Andric pair<value_type*, ptrdiff_t> __buf = _VSTD::get_temporary_buffer<value_type>(__buf_size); 47250b57cec5SDimitry Andric unique_ptr<value_type, __return_temporary_buffer> __h(__buf.first); 47260b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 47270b57cec5SDimitry Andric return _VSTD::__inplace_merge<_Comp_ref>(__first, __middle, __last, __comp, __len1, __len2, 47280b57cec5SDimitry Andric __buf.first, __buf.second); 47290b57cec5SDimitry Andric} 47300b57cec5SDimitry Andric 47310b57cec5SDimitry Andrictemplate <class _BidirectionalIterator> 47320b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 47330b57cec5SDimitry Andricvoid 47340b57cec5SDimitry Andricinplace_merge(_BidirectionalIterator __first, _BidirectionalIterator __middle, _BidirectionalIterator __last) 47350b57cec5SDimitry Andric{ 47360b57cec5SDimitry Andric _VSTD::inplace_merge(__first, __middle, __last, 47370b57cec5SDimitry Andric __less<typename iterator_traits<_BidirectionalIterator>::value_type>()); 47380b57cec5SDimitry Andric} 47390b57cec5SDimitry Andric 47400b57cec5SDimitry Andric// stable_sort 47410b57cec5SDimitry Andric 47420b57cec5SDimitry Andrictemplate <class _Compare, class _InputIterator1, class _InputIterator2> 47430b57cec5SDimitry Andricvoid 47440b57cec5SDimitry Andric__merge_move_construct(_InputIterator1 __first1, _InputIterator1 __last1, 47450b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, 47460b57cec5SDimitry Andric typename iterator_traits<_InputIterator1>::value_type* __result, _Compare __comp) 47470b57cec5SDimitry Andric{ 47480b57cec5SDimitry Andric typedef typename iterator_traits<_InputIterator1>::value_type value_type; 47490b57cec5SDimitry Andric __destruct_n __d(0); 47500b57cec5SDimitry Andric unique_ptr<value_type, __destruct_n&> __h(__result, __d); 47510b57cec5SDimitry Andric for (; true; ++__result) 47520b57cec5SDimitry Andric { 47530b57cec5SDimitry Andric if (__first1 == __last1) 47540b57cec5SDimitry Andric { 4755*e8d8bef9SDimitry Andric for (; __first2 != __last2; ++__first2, ++__result, (void)__d.template __incr<value_type>()) 4756*e8d8bef9SDimitry Andric ::new ((void*)__result) value_type(_VSTD::move(*__first2)); 47570b57cec5SDimitry Andric __h.release(); 47580b57cec5SDimitry Andric return; 47590b57cec5SDimitry Andric } 47600b57cec5SDimitry Andric if (__first2 == __last2) 47610b57cec5SDimitry Andric { 4762*e8d8bef9SDimitry Andric for (; __first1 != __last1; ++__first1, ++__result, (void)__d.template __incr<value_type>()) 4763*e8d8bef9SDimitry Andric ::new ((void*)__result) value_type(_VSTD::move(*__first1)); 47640b57cec5SDimitry Andric __h.release(); 47650b57cec5SDimitry Andric return; 47660b57cec5SDimitry Andric } 47670b57cec5SDimitry Andric if (__comp(*__first2, *__first1)) 47680b57cec5SDimitry Andric { 4769*e8d8bef9SDimitry Andric ::new ((void*)__result) value_type(_VSTD::move(*__first2)); 4770*e8d8bef9SDimitry Andric __d.template __incr<value_type>(); 47710b57cec5SDimitry Andric ++__first2; 47720b57cec5SDimitry Andric } 47730b57cec5SDimitry Andric else 47740b57cec5SDimitry Andric { 4775*e8d8bef9SDimitry Andric ::new ((void*)__result) value_type(_VSTD::move(*__first1)); 4776*e8d8bef9SDimitry Andric __d.template __incr<value_type>(); 47770b57cec5SDimitry Andric ++__first1; 47780b57cec5SDimitry Andric } 47790b57cec5SDimitry Andric } 47800b57cec5SDimitry Andric} 47810b57cec5SDimitry Andric 47820b57cec5SDimitry Andrictemplate <class _Compare, class _InputIterator1, class _InputIterator2, class _OutputIterator> 47830b57cec5SDimitry Andricvoid 47840b57cec5SDimitry Andric__merge_move_assign(_InputIterator1 __first1, _InputIterator1 __last1, 47850b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, 47860b57cec5SDimitry Andric _OutputIterator __result, _Compare __comp) 47870b57cec5SDimitry Andric{ 47880b57cec5SDimitry Andric for (; __first1 != __last1; ++__result) 47890b57cec5SDimitry Andric { 47900b57cec5SDimitry Andric if (__first2 == __last2) 47910b57cec5SDimitry Andric { 4792e40139ffSDimitry Andric for (; __first1 != __last1; ++__first1, (void) ++__result) 47930b57cec5SDimitry Andric *__result = _VSTD::move(*__first1); 47940b57cec5SDimitry Andric return; 47950b57cec5SDimitry Andric } 47960b57cec5SDimitry Andric if (__comp(*__first2, *__first1)) 47970b57cec5SDimitry Andric { 47980b57cec5SDimitry Andric *__result = _VSTD::move(*__first2); 47990b57cec5SDimitry Andric ++__first2; 48000b57cec5SDimitry Andric } 48010b57cec5SDimitry Andric else 48020b57cec5SDimitry Andric { 48030b57cec5SDimitry Andric *__result = _VSTD::move(*__first1); 48040b57cec5SDimitry Andric ++__first1; 48050b57cec5SDimitry Andric } 48060b57cec5SDimitry Andric } 4807e40139ffSDimitry Andric for (; __first2 != __last2; ++__first2, (void) ++__result) 48080b57cec5SDimitry Andric *__result = _VSTD::move(*__first2); 48090b57cec5SDimitry Andric} 48100b57cec5SDimitry Andric 48110b57cec5SDimitry Andrictemplate <class _Compare, class _RandomAccessIterator> 48120b57cec5SDimitry Andricvoid 48130b57cec5SDimitry Andric__stable_sort(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp, 48140b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator>::difference_type __len, 48150b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator>::value_type* __buff, ptrdiff_t __buff_size); 48160b57cec5SDimitry Andric 48170b57cec5SDimitry Andrictemplate <class _Compare, class _RandomAccessIterator> 48180b57cec5SDimitry Andricvoid 48190b57cec5SDimitry Andric__stable_sort_move(_RandomAccessIterator __first1, _RandomAccessIterator __last1, _Compare __comp, 48200b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator>::difference_type __len, 48210b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator>::value_type* __first2) 48220b57cec5SDimitry Andric{ 48230b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::value_type value_type; 48240b57cec5SDimitry Andric switch (__len) 48250b57cec5SDimitry Andric { 48260b57cec5SDimitry Andric case 0: 48270b57cec5SDimitry Andric return; 48280b57cec5SDimitry Andric case 1: 4829*e8d8bef9SDimitry Andric ::new ((void*)__first2) value_type(_VSTD::move(*__first1)); 48300b57cec5SDimitry Andric return; 48310b57cec5SDimitry Andric case 2: 48320b57cec5SDimitry Andric __destruct_n __d(0); 48330b57cec5SDimitry Andric unique_ptr<value_type, __destruct_n&> __h2(__first2, __d); 48340b57cec5SDimitry Andric if (__comp(*--__last1, *__first1)) 48350b57cec5SDimitry Andric { 4836*e8d8bef9SDimitry Andric ::new ((void*)__first2) value_type(_VSTD::move(*__last1)); 4837*e8d8bef9SDimitry Andric __d.template __incr<value_type>(); 48380b57cec5SDimitry Andric ++__first2; 4839*e8d8bef9SDimitry Andric ::new ((void*)__first2) value_type(_VSTD::move(*__first1)); 48400b57cec5SDimitry Andric } 48410b57cec5SDimitry Andric else 48420b57cec5SDimitry Andric { 4843*e8d8bef9SDimitry Andric ::new ((void*)__first2) value_type(_VSTD::move(*__first1)); 4844*e8d8bef9SDimitry Andric __d.template __incr<value_type>(); 48450b57cec5SDimitry Andric ++__first2; 4846*e8d8bef9SDimitry Andric ::new ((void*)__first2) value_type(_VSTD::move(*__last1)); 48470b57cec5SDimitry Andric } 48480b57cec5SDimitry Andric __h2.release(); 48490b57cec5SDimitry Andric return; 48500b57cec5SDimitry Andric } 48510b57cec5SDimitry Andric if (__len <= 8) 48520b57cec5SDimitry Andric { 4853*e8d8bef9SDimitry Andric _VSTD::__insertion_sort_move<_Compare>(__first1, __last1, __first2, __comp); 48540b57cec5SDimitry Andric return; 48550b57cec5SDimitry Andric } 48560b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator>::difference_type __l2 = __len / 2; 48570b57cec5SDimitry Andric _RandomAccessIterator __m = __first1 + __l2; 4858*e8d8bef9SDimitry Andric _VSTD::__stable_sort<_Compare>(__first1, __m, __comp, __l2, __first2, __l2); 4859*e8d8bef9SDimitry Andric _VSTD::__stable_sort<_Compare>(__m, __last1, __comp, __len - __l2, __first2 + __l2, __len - __l2); 4860*e8d8bef9SDimitry Andric _VSTD::__merge_move_construct<_Compare>(__first1, __m, __m, __last1, __first2, __comp); 48610b57cec5SDimitry Andric} 48620b57cec5SDimitry Andric 48630b57cec5SDimitry Andrictemplate <class _Tp> 48640b57cec5SDimitry Andricstruct __stable_sort_switch 48650b57cec5SDimitry Andric{ 48660b57cec5SDimitry Andric static const unsigned value = 128*is_trivially_copy_assignable<_Tp>::value; 48670b57cec5SDimitry Andric}; 48680b57cec5SDimitry Andric 48690b57cec5SDimitry Andrictemplate <class _Compare, class _RandomAccessIterator> 48700b57cec5SDimitry Andricvoid 48710b57cec5SDimitry Andric__stable_sort(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp, 48720b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator>::difference_type __len, 48730b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator>::value_type* __buff, ptrdiff_t __buff_size) 48740b57cec5SDimitry Andric{ 48750b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::value_type value_type; 48760b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::difference_type difference_type; 48770b57cec5SDimitry Andric switch (__len) 48780b57cec5SDimitry Andric { 48790b57cec5SDimitry Andric case 0: 48800b57cec5SDimitry Andric case 1: 48810b57cec5SDimitry Andric return; 48820b57cec5SDimitry Andric case 2: 48830b57cec5SDimitry Andric if (__comp(*--__last, *__first)) 48840b57cec5SDimitry Andric swap(*__first, *__last); 48850b57cec5SDimitry Andric return; 48860b57cec5SDimitry Andric } 48870b57cec5SDimitry Andric if (__len <= static_cast<difference_type>(__stable_sort_switch<value_type>::value)) 48880b57cec5SDimitry Andric { 4889*e8d8bef9SDimitry Andric _VSTD::__insertion_sort<_Compare>(__first, __last, __comp); 48900b57cec5SDimitry Andric return; 48910b57cec5SDimitry Andric } 48920b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator>::difference_type __l2 = __len / 2; 48930b57cec5SDimitry Andric _RandomAccessIterator __m = __first + __l2; 48940b57cec5SDimitry Andric if (__len <= __buff_size) 48950b57cec5SDimitry Andric { 48960b57cec5SDimitry Andric __destruct_n __d(0); 48970b57cec5SDimitry Andric unique_ptr<value_type, __destruct_n&> __h2(__buff, __d); 4898*e8d8bef9SDimitry Andric _VSTD::__stable_sort_move<_Compare>(__first, __m, __comp, __l2, __buff); 4899*e8d8bef9SDimitry Andric __d.__set(__l2, (value_type*)nullptr); 4900*e8d8bef9SDimitry Andric _VSTD::__stable_sort_move<_Compare>(__m, __last, __comp, __len - __l2, __buff + __l2); 4901*e8d8bef9SDimitry Andric __d.__set(__len, (value_type*)nullptr); 4902*e8d8bef9SDimitry Andric _VSTD::__merge_move_assign<_Compare>(__buff, __buff + __l2, __buff + __l2, __buff + __len, __first, __comp); 4903*e8d8bef9SDimitry Andric// _VSTD::__merge<_Compare>(move_iterator<value_type*>(__buff), 49040b57cec5SDimitry Andric// move_iterator<value_type*>(__buff + __l2), 49050b57cec5SDimitry Andric// move_iterator<_RandomAccessIterator>(__buff + __l2), 49060b57cec5SDimitry Andric// move_iterator<_RandomAccessIterator>(__buff + __len), 49070b57cec5SDimitry Andric// __first, __comp); 49080b57cec5SDimitry Andric return; 49090b57cec5SDimitry Andric } 4910*e8d8bef9SDimitry Andric _VSTD::__stable_sort<_Compare>(__first, __m, __comp, __l2, __buff, __buff_size); 4911*e8d8bef9SDimitry Andric _VSTD::__stable_sort<_Compare>(__m, __last, __comp, __len - __l2, __buff, __buff_size); 4912*e8d8bef9SDimitry Andric _VSTD::__inplace_merge<_Compare>(__first, __m, __last, __comp, __l2, __len - __l2, __buff, __buff_size); 49130b57cec5SDimitry Andric} 49140b57cec5SDimitry Andric 49150b57cec5SDimitry Andrictemplate <class _RandomAccessIterator, class _Compare> 49160b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 49170b57cec5SDimitry Andricvoid 49180b57cec5SDimitry Andricstable_sort(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) 49190b57cec5SDimitry Andric{ 49200b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::value_type value_type; 49210b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::difference_type difference_type; 49220b57cec5SDimitry Andric difference_type __len = __last - __first; 49230b57cec5SDimitry Andric pair<value_type*, ptrdiff_t> __buf(0, 0); 49240b57cec5SDimitry Andric unique_ptr<value_type, __return_temporary_buffer> __h; 49250b57cec5SDimitry Andric if (__len > static_cast<difference_type>(__stable_sort_switch<value_type>::value)) 49260b57cec5SDimitry Andric { 49270b57cec5SDimitry Andric __buf = _VSTD::get_temporary_buffer<value_type>(__len); 49280b57cec5SDimitry Andric __h.reset(__buf.first); 49290b57cec5SDimitry Andric } 49300b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 4931*e8d8bef9SDimitry Andric _VSTD::__stable_sort<_Comp_ref>(__first, __last, __comp, __len, __buf.first, __buf.second); 49320b57cec5SDimitry Andric} 49330b57cec5SDimitry Andric 49340b57cec5SDimitry Andrictemplate <class _RandomAccessIterator> 49350b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 49360b57cec5SDimitry Andricvoid 49370b57cec5SDimitry Andricstable_sort(_RandomAccessIterator __first, _RandomAccessIterator __last) 49380b57cec5SDimitry Andric{ 49390b57cec5SDimitry Andric _VSTD::stable_sort(__first, __last, __less<typename iterator_traits<_RandomAccessIterator>::value_type>()); 49400b57cec5SDimitry Andric} 49410b57cec5SDimitry Andric 49420b57cec5SDimitry Andric// is_heap_until 49430b57cec5SDimitry Andric 49440b57cec5SDimitry Andrictemplate <class _RandomAccessIterator, class _Compare> 49450b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT _LIBCPP_CONSTEXPR_AFTER_CXX17 _RandomAccessIterator 49460b57cec5SDimitry Andricis_heap_until(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) 49470b57cec5SDimitry Andric{ 49480b57cec5SDimitry Andric typedef typename _VSTD::iterator_traits<_RandomAccessIterator>::difference_type difference_type; 49490b57cec5SDimitry Andric difference_type __len = __last - __first; 49500b57cec5SDimitry Andric difference_type __p = 0; 49510b57cec5SDimitry Andric difference_type __c = 1; 49520b57cec5SDimitry Andric _RandomAccessIterator __pp = __first; 49530b57cec5SDimitry Andric while (__c < __len) 49540b57cec5SDimitry Andric { 49550b57cec5SDimitry Andric _RandomAccessIterator __cp = __first + __c; 49560b57cec5SDimitry Andric if (__comp(*__pp, *__cp)) 49570b57cec5SDimitry Andric return __cp; 49580b57cec5SDimitry Andric ++__c; 49590b57cec5SDimitry Andric ++__cp; 49600b57cec5SDimitry Andric if (__c == __len) 49610b57cec5SDimitry Andric return __last; 49620b57cec5SDimitry Andric if (__comp(*__pp, *__cp)) 49630b57cec5SDimitry Andric return __cp; 49640b57cec5SDimitry Andric ++__p; 49650b57cec5SDimitry Andric ++__pp; 49660b57cec5SDimitry Andric __c = 2 * __p + 1; 49670b57cec5SDimitry Andric } 49680b57cec5SDimitry Andric return __last; 49690b57cec5SDimitry Andric} 49700b57cec5SDimitry Andric 49710b57cec5SDimitry Andrictemplate<class _RandomAccessIterator> 49720b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 49730b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 49740b57cec5SDimitry Andric_RandomAccessIterator 49750b57cec5SDimitry Andricis_heap_until(_RandomAccessIterator __first, _RandomAccessIterator __last) 49760b57cec5SDimitry Andric{ 49770b57cec5SDimitry Andric return _VSTD::is_heap_until(__first, __last, __less<typename iterator_traits<_RandomAccessIterator>::value_type>()); 49780b57cec5SDimitry Andric} 49790b57cec5SDimitry Andric 49800b57cec5SDimitry Andric// is_heap 49810b57cec5SDimitry Andric 49820b57cec5SDimitry Andrictemplate <class _RandomAccessIterator, class _Compare> 49830b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 49840b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 49850b57cec5SDimitry Andricbool 49860b57cec5SDimitry Andricis_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) 49870b57cec5SDimitry Andric{ 49880b57cec5SDimitry Andric return _VSTD::is_heap_until(__first, __last, __comp) == __last; 49890b57cec5SDimitry Andric} 49900b57cec5SDimitry Andric 49910b57cec5SDimitry Andrictemplate<class _RandomAccessIterator> 49920b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 49930b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 49940b57cec5SDimitry Andricbool 49950b57cec5SDimitry Andricis_heap(_RandomAccessIterator __first, _RandomAccessIterator __last) 49960b57cec5SDimitry Andric{ 49970b57cec5SDimitry Andric return _VSTD::is_heap(__first, __last, __less<typename iterator_traits<_RandomAccessIterator>::value_type>()); 49980b57cec5SDimitry Andric} 49990b57cec5SDimitry Andric 50000b57cec5SDimitry Andric// push_heap 50010b57cec5SDimitry Andric 50020b57cec5SDimitry Andrictemplate <class _Compare, class _RandomAccessIterator> 50030b57cec5SDimitry Andricvoid 50040b57cec5SDimitry Andric__sift_up(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp, 50050b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator>::difference_type __len) 50060b57cec5SDimitry Andric{ 50070b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::value_type value_type; 50080b57cec5SDimitry Andric if (__len > 1) 50090b57cec5SDimitry Andric { 50100b57cec5SDimitry Andric __len = (__len - 2) / 2; 50110b57cec5SDimitry Andric _RandomAccessIterator __ptr = __first + __len; 50120b57cec5SDimitry Andric if (__comp(*__ptr, *--__last)) 50130b57cec5SDimitry Andric { 50140b57cec5SDimitry Andric value_type __t(_VSTD::move(*__last)); 50150b57cec5SDimitry Andric do 50160b57cec5SDimitry Andric { 50170b57cec5SDimitry Andric *__last = _VSTD::move(*__ptr); 50180b57cec5SDimitry Andric __last = __ptr; 50190b57cec5SDimitry Andric if (__len == 0) 50200b57cec5SDimitry Andric break; 50210b57cec5SDimitry Andric __len = (__len - 1) / 2; 50220b57cec5SDimitry Andric __ptr = __first + __len; 50230b57cec5SDimitry Andric } while (__comp(*__ptr, __t)); 50240b57cec5SDimitry Andric *__last = _VSTD::move(__t); 50250b57cec5SDimitry Andric } 50260b57cec5SDimitry Andric } 50270b57cec5SDimitry Andric} 50280b57cec5SDimitry Andric 50290b57cec5SDimitry Andrictemplate <class _RandomAccessIterator, class _Compare> 50300b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 50310b57cec5SDimitry Andricvoid 50320b57cec5SDimitry Andricpush_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) 50330b57cec5SDimitry Andric{ 50340b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5035*e8d8bef9SDimitry Andric _VSTD::__sift_up<_Comp_ref>(__first, __last, __comp, __last - __first); 50360b57cec5SDimitry Andric} 50370b57cec5SDimitry Andric 50380b57cec5SDimitry Andrictemplate <class _RandomAccessIterator> 50390b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 50400b57cec5SDimitry Andricvoid 50410b57cec5SDimitry Andricpush_heap(_RandomAccessIterator __first, _RandomAccessIterator __last) 50420b57cec5SDimitry Andric{ 50430b57cec5SDimitry Andric _VSTD::push_heap(__first, __last, __less<typename iterator_traits<_RandomAccessIterator>::value_type>()); 50440b57cec5SDimitry Andric} 50450b57cec5SDimitry Andric 50460b57cec5SDimitry Andric// pop_heap 50470b57cec5SDimitry Andric 50480b57cec5SDimitry Andrictemplate <class _Compare, class _RandomAccessIterator> 50490b57cec5SDimitry Andricvoid 50500b57cec5SDimitry Andric__sift_down(_RandomAccessIterator __first, _RandomAccessIterator /*__last*/, 50510b57cec5SDimitry Andric _Compare __comp, 50520b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator>::difference_type __len, 50530b57cec5SDimitry Andric _RandomAccessIterator __start) 50540b57cec5SDimitry Andric{ 50550b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::difference_type difference_type; 50560b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::value_type value_type; 50570b57cec5SDimitry Andric // left-child of __start is at 2 * __start + 1 50580b57cec5SDimitry Andric // right-child of __start is at 2 * __start + 2 50590b57cec5SDimitry Andric difference_type __child = __start - __first; 50600b57cec5SDimitry Andric 50610b57cec5SDimitry Andric if (__len < 2 || (__len - 2) / 2 < __child) 50620b57cec5SDimitry Andric return; 50630b57cec5SDimitry Andric 50640b57cec5SDimitry Andric __child = 2 * __child + 1; 50650b57cec5SDimitry Andric _RandomAccessIterator __child_i = __first + __child; 50660b57cec5SDimitry Andric 50670b57cec5SDimitry Andric if ((__child + 1) < __len && __comp(*__child_i, *(__child_i + 1))) { 50680b57cec5SDimitry Andric // right-child exists and is greater than left-child 50690b57cec5SDimitry Andric ++__child_i; 50700b57cec5SDimitry Andric ++__child; 50710b57cec5SDimitry Andric } 50720b57cec5SDimitry Andric 50730b57cec5SDimitry Andric // check if we are in heap-order 50740b57cec5SDimitry Andric if (__comp(*__child_i, *__start)) 50750b57cec5SDimitry Andric // we are, __start is larger than it's largest child 50760b57cec5SDimitry Andric return; 50770b57cec5SDimitry Andric 50780b57cec5SDimitry Andric value_type __top(_VSTD::move(*__start)); 50790b57cec5SDimitry Andric do 50800b57cec5SDimitry Andric { 50810b57cec5SDimitry Andric // we are not in heap-order, swap the parent with it's largest child 50820b57cec5SDimitry Andric *__start = _VSTD::move(*__child_i); 50830b57cec5SDimitry Andric __start = __child_i; 50840b57cec5SDimitry Andric 50850b57cec5SDimitry Andric if ((__len - 2) / 2 < __child) 50860b57cec5SDimitry Andric break; 50870b57cec5SDimitry Andric 50880b57cec5SDimitry Andric // recompute the child based off of the updated parent 50890b57cec5SDimitry Andric __child = 2 * __child + 1; 50900b57cec5SDimitry Andric __child_i = __first + __child; 50910b57cec5SDimitry Andric 50920b57cec5SDimitry Andric if ((__child + 1) < __len && __comp(*__child_i, *(__child_i + 1))) { 50930b57cec5SDimitry Andric // right-child exists and is greater than left-child 50940b57cec5SDimitry Andric ++__child_i; 50950b57cec5SDimitry Andric ++__child; 50960b57cec5SDimitry Andric } 50970b57cec5SDimitry Andric 50980b57cec5SDimitry Andric // check if we are in heap-order 50990b57cec5SDimitry Andric } while (!__comp(*__child_i, __top)); 51000b57cec5SDimitry Andric *__start = _VSTD::move(__top); 51010b57cec5SDimitry Andric} 51020b57cec5SDimitry Andric 51030b57cec5SDimitry Andrictemplate <class _Compare, class _RandomAccessIterator> 51040b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 51050b57cec5SDimitry Andricvoid 51060b57cec5SDimitry Andric__pop_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp, 51070b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator>::difference_type __len) 51080b57cec5SDimitry Andric{ 51090b57cec5SDimitry Andric if (__len > 1) 51100b57cec5SDimitry Andric { 51110b57cec5SDimitry Andric swap(*__first, *--__last); 5112*e8d8bef9SDimitry Andric _VSTD::__sift_down<_Compare>(__first, __last, __comp, __len - 1, __first); 51130b57cec5SDimitry Andric } 51140b57cec5SDimitry Andric} 51150b57cec5SDimitry Andric 51160b57cec5SDimitry Andrictemplate <class _RandomAccessIterator, class _Compare> 51170b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 51180b57cec5SDimitry Andricvoid 51190b57cec5SDimitry Andricpop_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) 51200b57cec5SDimitry Andric{ 51210b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5122*e8d8bef9SDimitry Andric _VSTD::__pop_heap<_Comp_ref>(__first, __last, __comp, __last - __first); 51230b57cec5SDimitry Andric} 51240b57cec5SDimitry Andric 51250b57cec5SDimitry Andrictemplate <class _RandomAccessIterator> 51260b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 51270b57cec5SDimitry Andricvoid 51280b57cec5SDimitry Andricpop_heap(_RandomAccessIterator __first, _RandomAccessIterator __last) 51290b57cec5SDimitry Andric{ 51300b57cec5SDimitry Andric _VSTD::pop_heap(__first, __last, __less<typename iterator_traits<_RandomAccessIterator>::value_type>()); 51310b57cec5SDimitry Andric} 51320b57cec5SDimitry Andric 51330b57cec5SDimitry Andric// make_heap 51340b57cec5SDimitry Andric 51350b57cec5SDimitry Andrictemplate <class _Compare, class _RandomAccessIterator> 51360b57cec5SDimitry Andricvoid 51370b57cec5SDimitry Andric__make_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) 51380b57cec5SDimitry Andric{ 51390b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::difference_type difference_type; 51400b57cec5SDimitry Andric difference_type __n = __last - __first; 51410b57cec5SDimitry Andric if (__n > 1) 51420b57cec5SDimitry Andric { 51430b57cec5SDimitry Andric // start from the first parent, there is no need to consider children 51440b57cec5SDimitry Andric for (difference_type __start = (__n - 2) / 2; __start >= 0; --__start) 51450b57cec5SDimitry Andric { 5146*e8d8bef9SDimitry Andric _VSTD::__sift_down<_Compare>(__first, __last, __comp, __n, __first + __start); 51470b57cec5SDimitry Andric } 51480b57cec5SDimitry Andric } 51490b57cec5SDimitry Andric} 51500b57cec5SDimitry Andric 51510b57cec5SDimitry Andrictemplate <class _RandomAccessIterator, class _Compare> 51520b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 51530b57cec5SDimitry Andricvoid 51540b57cec5SDimitry Andricmake_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) 51550b57cec5SDimitry Andric{ 51560b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5157*e8d8bef9SDimitry Andric _VSTD::__make_heap<_Comp_ref>(__first, __last, __comp); 51580b57cec5SDimitry Andric} 51590b57cec5SDimitry Andric 51600b57cec5SDimitry Andrictemplate <class _RandomAccessIterator> 51610b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 51620b57cec5SDimitry Andricvoid 51630b57cec5SDimitry Andricmake_heap(_RandomAccessIterator __first, _RandomAccessIterator __last) 51640b57cec5SDimitry Andric{ 51650b57cec5SDimitry Andric _VSTD::make_heap(__first, __last, __less<typename iterator_traits<_RandomAccessIterator>::value_type>()); 51660b57cec5SDimitry Andric} 51670b57cec5SDimitry Andric 51680b57cec5SDimitry Andric// sort_heap 51690b57cec5SDimitry Andric 51700b57cec5SDimitry Andrictemplate <class _Compare, class _RandomAccessIterator> 51710b57cec5SDimitry Andricvoid 51720b57cec5SDimitry Andric__sort_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) 51730b57cec5SDimitry Andric{ 51740b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::difference_type difference_type; 5175e40139ffSDimitry Andric for (difference_type __n = __last - __first; __n > 1; --__last, (void) --__n) 5176*e8d8bef9SDimitry Andric _VSTD::__pop_heap<_Compare>(__first, __last, __comp, __n); 51770b57cec5SDimitry Andric} 51780b57cec5SDimitry Andric 51790b57cec5SDimitry Andrictemplate <class _RandomAccessIterator, class _Compare> 51800b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 51810b57cec5SDimitry Andricvoid 51820b57cec5SDimitry Andricsort_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) 51830b57cec5SDimitry Andric{ 51840b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5185*e8d8bef9SDimitry Andric _VSTD::__sort_heap<_Comp_ref>(__first, __last, __comp); 51860b57cec5SDimitry Andric} 51870b57cec5SDimitry Andric 51880b57cec5SDimitry Andrictemplate <class _RandomAccessIterator> 51890b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 51900b57cec5SDimitry Andricvoid 51910b57cec5SDimitry Andricsort_heap(_RandomAccessIterator __first, _RandomAccessIterator __last) 51920b57cec5SDimitry Andric{ 51930b57cec5SDimitry Andric _VSTD::sort_heap(__first, __last, __less<typename iterator_traits<_RandomAccessIterator>::value_type>()); 51940b57cec5SDimitry Andric} 51950b57cec5SDimitry Andric 51960b57cec5SDimitry Andric// partial_sort 51970b57cec5SDimitry Andric 51980b57cec5SDimitry Andrictemplate <class _Compare, class _RandomAccessIterator> 51990b57cec5SDimitry Andricvoid 52000b57cec5SDimitry Andric__partial_sort(_RandomAccessIterator __first, _RandomAccessIterator __middle, _RandomAccessIterator __last, 52010b57cec5SDimitry Andric _Compare __comp) 52020b57cec5SDimitry Andric{ 5203*e8d8bef9SDimitry Andric _VSTD::__make_heap<_Compare>(__first, __middle, __comp); 52040b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator>::difference_type __len = __middle - __first; 52050b57cec5SDimitry Andric for (_RandomAccessIterator __i = __middle; __i != __last; ++__i) 52060b57cec5SDimitry Andric { 52070b57cec5SDimitry Andric if (__comp(*__i, *__first)) 52080b57cec5SDimitry Andric { 52090b57cec5SDimitry Andric swap(*__i, *__first); 5210*e8d8bef9SDimitry Andric _VSTD::__sift_down<_Compare>(__first, __middle, __comp, __len, __first); 52110b57cec5SDimitry Andric } 52120b57cec5SDimitry Andric } 5213*e8d8bef9SDimitry Andric _VSTD::__sort_heap<_Compare>(__first, __middle, __comp); 52140b57cec5SDimitry Andric} 52150b57cec5SDimitry Andric 52160b57cec5SDimitry Andrictemplate <class _RandomAccessIterator, class _Compare> 52170b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 52180b57cec5SDimitry Andricvoid 52190b57cec5SDimitry Andricpartial_sort(_RandomAccessIterator __first, _RandomAccessIterator __middle, _RandomAccessIterator __last, 52200b57cec5SDimitry Andric _Compare __comp) 52210b57cec5SDimitry Andric{ 52220b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5223*e8d8bef9SDimitry Andric _VSTD::__partial_sort<_Comp_ref>(__first, __middle, __last, __comp); 52240b57cec5SDimitry Andric} 52250b57cec5SDimitry Andric 52260b57cec5SDimitry Andrictemplate <class _RandomAccessIterator> 52270b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 52280b57cec5SDimitry Andricvoid 52290b57cec5SDimitry Andricpartial_sort(_RandomAccessIterator __first, _RandomAccessIterator __middle, _RandomAccessIterator __last) 52300b57cec5SDimitry Andric{ 52310b57cec5SDimitry Andric _VSTD::partial_sort(__first, __middle, __last, 52320b57cec5SDimitry Andric __less<typename iterator_traits<_RandomAccessIterator>::value_type>()); 52330b57cec5SDimitry Andric} 52340b57cec5SDimitry Andric 52350b57cec5SDimitry Andric// partial_sort_copy 52360b57cec5SDimitry Andric 52370b57cec5SDimitry Andrictemplate <class _Compare, class _InputIterator, class _RandomAccessIterator> 52380b57cec5SDimitry Andric_RandomAccessIterator 52390b57cec5SDimitry Andric__partial_sort_copy(_InputIterator __first, _InputIterator __last, 52400b57cec5SDimitry Andric _RandomAccessIterator __result_first, _RandomAccessIterator __result_last, _Compare __comp) 52410b57cec5SDimitry Andric{ 52420b57cec5SDimitry Andric _RandomAccessIterator __r = __result_first; 52430b57cec5SDimitry Andric if (__r != __result_last) 52440b57cec5SDimitry Andric { 5245e40139ffSDimitry Andric for (; __first != __last && __r != __result_last; ++__first, (void) ++__r) 52460b57cec5SDimitry Andric *__r = *__first; 5247*e8d8bef9SDimitry Andric _VSTD::__make_heap<_Compare>(__result_first, __r, __comp); 52480b57cec5SDimitry Andric typename iterator_traits<_RandomAccessIterator>::difference_type __len = __r - __result_first; 52490b57cec5SDimitry Andric for (; __first != __last; ++__first) 52500b57cec5SDimitry Andric if (__comp(*__first, *__result_first)) 52510b57cec5SDimitry Andric { 52520b57cec5SDimitry Andric *__result_first = *__first; 5253*e8d8bef9SDimitry Andric _VSTD::__sift_down<_Compare>(__result_first, __r, __comp, __len, __result_first); 52540b57cec5SDimitry Andric } 5255*e8d8bef9SDimitry Andric _VSTD::__sort_heap<_Compare>(__result_first, __r, __comp); 52560b57cec5SDimitry Andric } 52570b57cec5SDimitry Andric return __r; 52580b57cec5SDimitry Andric} 52590b57cec5SDimitry Andric 52600b57cec5SDimitry Andrictemplate <class _InputIterator, class _RandomAccessIterator, class _Compare> 52610b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 52620b57cec5SDimitry Andric_RandomAccessIterator 52630b57cec5SDimitry Andricpartial_sort_copy(_InputIterator __first, _InputIterator __last, 52640b57cec5SDimitry Andric _RandomAccessIterator __result_first, _RandomAccessIterator __result_last, _Compare __comp) 52650b57cec5SDimitry Andric{ 52660b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5267*e8d8bef9SDimitry Andric return _VSTD::__partial_sort_copy<_Comp_ref>(__first, __last, __result_first, __result_last, __comp); 52680b57cec5SDimitry Andric} 52690b57cec5SDimitry Andric 52700b57cec5SDimitry Andrictemplate <class _InputIterator, class _RandomAccessIterator> 52710b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 52720b57cec5SDimitry Andric_RandomAccessIterator 52730b57cec5SDimitry Andricpartial_sort_copy(_InputIterator __first, _InputIterator __last, 52740b57cec5SDimitry Andric _RandomAccessIterator __result_first, _RandomAccessIterator __result_last) 52750b57cec5SDimitry Andric{ 52760b57cec5SDimitry Andric return _VSTD::partial_sort_copy(__first, __last, __result_first, __result_last, 52770b57cec5SDimitry Andric __less<typename iterator_traits<_RandomAccessIterator>::value_type>()); 52780b57cec5SDimitry Andric} 52790b57cec5SDimitry Andric 52800b57cec5SDimitry Andric// nth_element 52810b57cec5SDimitry Andric 52820b57cec5SDimitry Andrictemplate <class _Compare, class _RandomAccessIterator> 52830b57cec5SDimitry Andricvoid 52840b57cec5SDimitry Andric__nth_element(_RandomAccessIterator __first, _RandomAccessIterator __nth, _RandomAccessIterator __last, _Compare __comp) 52850b57cec5SDimitry Andric{ 52860b57cec5SDimitry Andric // _Compare is known to be a reference type 52870b57cec5SDimitry Andric typedef typename iterator_traits<_RandomAccessIterator>::difference_type difference_type; 52880b57cec5SDimitry Andric const difference_type __limit = 7; 52890b57cec5SDimitry Andric while (true) 52900b57cec5SDimitry Andric { 52910b57cec5SDimitry Andric __restart: 52920b57cec5SDimitry Andric if (__nth == __last) 52930b57cec5SDimitry Andric return; 52940b57cec5SDimitry Andric difference_type __len = __last - __first; 52950b57cec5SDimitry Andric switch (__len) 52960b57cec5SDimitry Andric { 52970b57cec5SDimitry Andric case 0: 52980b57cec5SDimitry Andric case 1: 52990b57cec5SDimitry Andric return; 53000b57cec5SDimitry Andric case 2: 53010b57cec5SDimitry Andric if (__comp(*--__last, *__first)) 53020b57cec5SDimitry Andric swap(*__first, *__last); 53030b57cec5SDimitry Andric return; 53040b57cec5SDimitry Andric case 3: 53050b57cec5SDimitry Andric { 53060b57cec5SDimitry Andric _RandomAccessIterator __m = __first; 53070b57cec5SDimitry Andric _VSTD::__sort3<_Compare>(__first, ++__m, --__last, __comp); 53080b57cec5SDimitry Andric return; 53090b57cec5SDimitry Andric } 53100b57cec5SDimitry Andric } 53110b57cec5SDimitry Andric if (__len <= __limit) 53120b57cec5SDimitry Andric { 5313*e8d8bef9SDimitry Andric _VSTD::__selection_sort<_Compare>(__first, __last, __comp); 53140b57cec5SDimitry Andric return; 53150b57cec5SDimitry Andric } 53160b57cec5SDimitry Andric // __len > __limit >= 3 53170b57cec5SDimitry Andric _RandomAccessIterator __m = __first + __len/2; 53180b57cec5SDimitry Andric _RandomAccessIterator __lm1 = __last; 53190b57cec5SDimitry Andric unsigned __n_swaps = _VSTD::__sort3<_Compare>(__first, __m, --__lm1, __comp); 53200b57cec5SDimitry Andric // *__m is median 53210b57cec5SDimitry Andric // partition [__first, __m) < *__m and *__m <= [__m, __last) 53220b57cec5SDimitry Andric // (this inhibits tossing elements equivalent to __m around unnecessarily) 53230b57cec5SDimitry Andric _RandomAccessIterator __i = __first; 53240b57cec5SDimitry Andric _RandomAccessIterator __j = __lm1; 53250b57cec5SDimitry Andric // j points beyond range to be tested, *__lm1 is known to be <= *__m 53260b57cec5SDimitry Andric // The search going up is known to be guarded but the search coming down isn't. 53270b57cec5SDimitry Andric // Prime the downward search with a guard. 53280b57cec5SDimitry Andric if (!__comp(*__i, *__m)) // if *__first == *__m 53290b57cec5SDimitry Andric { 53300b57cec5SDimitry Andric // *__first == *__m, *__first doesn't go in first part 53310b57cec5SDimitry Andric // manually guard downward moving __j against __i 53320b57cec5SDimitry Andric while (true) 53330b57cec5SDimitry Andric { 53340b57cec5SDimitry Andric if (__i == --__j) 53350b57cec5SDimitry Andric { 53360b57cec5SDimitry Andric // *__first == *__m, *__m <= all other elements 5337*e8d8bef9SDimitry Andric // Partition instead into [__first, __i) == *__first and *__first < [__i, __last) 53380b57cec5SDimitry Andric ++__i; // __first + 1 53390b57cec5SDimitry Andric __j = __last; 53400b57cec5SDimitry Andric if (!__comp(*__first, *--__j)) // we need a guard if *__first == *(__last-1) 53410b57cec5SDimitry Andric { 53420b57cec5SDimitry Andric while (true) 53430b57cec5SDimitry Andric { 53440b57cec5SDimitry Andric if (__i == __j) 53450b57cec5SDimitry Andric return; // [__first, __last) all equivalent elements 53460b57cec5SDimitry Andric if (__comp(*__first, *__i)) 53470b57cec5SDimitry Andric { 53480b57cec5SDimitry Andric swap(*__i, *__j); 53490b57cec5SDimitry Andric ++__n_swaps; 53500b57cec5SDimitry Andric ++__i; 53510b57cec5SDimitry Andric break; 53520b57cec5SDimitry Andric } 53530b57cec5SDimitry Andric ++__i; 53540b57cec5SDimitry Andric } 53550b57cec5SDimitry Andric } 53560b57cec5SDimitry Andric // [__first, __i) == *__first and *__first < [__j, __last) and __j == __last - 1 53570b57cec5SDimitry Andric if (__i == __j) 53580b57cec5SDimitry Andric return; 53590b57cec5SDimitry Andric while (true) 53600b57cec5SDimitry Andric { 53610b57cec5SDimitry Andric while (!__comp(*__first, *__i)) 53620b57cec5SDimitry Andric ++__i; 53630b57cec5SDimitry Andric while (__comp(*__first, *--__j)) 53640b57cec5SDimitry Andric ; 53650b57cec5SDimitry Andric if (__i >= __j) 53660b57cec5SDimitry Andric break; 53670b57cec5SDimitry Andric swap(*__i, *__j); 53680b57cec5SDimitry Andric ++__n_swaps; 53690b57cec5SDimitry Andric ++__i; 53700b57cec5SDimitry Andric } 53710b57cec5SDimitry Andric // [__first, __i) == *__first and *__first < [__i, __last) 53720b57cec5SDimitry Andric // The first part is sorted, 53730b57cec5SDimitry Andric if (__nth < __i) 53740b57cec5SDimitry Andric return; 5375*e8d8bef9SDimitry Andric // __nth_element the second part 5376*e8d8bef9SDimitry Andric // _VSTD::__nth_element<_Compare>(__i, __nth, __last, __comp); 53770b57cec5SDimitry Andric __first = __i; 53780b57cec5SDimitry Andric goto __restart; 53790b57cec5SDimitry Andric } 53800b57cec5SDimitry Andric if (__comp(*__j, *__m)) 53810b57cec5SDimitry Andric { 53820b57cec5SDimitry Andric swap(*__i, *__j); 53830b57cec5SDimitry Andric ++__n_swaps; 53840b57cec5SDimitry Andric break; // found guard for downward moving __j, now use unguarded partition 53850b57cec5SDimitry Andric } 53860b57cec5SDimitry Andric } 53870b57cec5SDimitry Andric } 53880b57cec5SDimitry Andric ++__i; 53890b57cec5SDimitry Andric // j points beyond range to be tested, *__lm1 is known to be <= *__m 53900b57cec5SDimitry Andric // if not yet partitioned... 53910b57cec5SDimitry Andric if (__i < __j) 53920b57cec5SDimitry Andric { 53930b57cec5SDimitry Andric // known that *(__i - 1) < *__m 53940b57cec5SDimitry Andric while (true) 53950b57cec5SDimitry Andric { 53960b57cec5SDimitry Andric // __m still guards upward moving __i 53970b57cec5SDimitry Andric while (__comp(*__i, *__m)) 53980b57cec5SDimitry Andric ++__i; 53990b57cec5SDimitry Andric // It is now known that a guard exists for downward moving __j 54000b57cec5SDimitry Andric while (!__comp(*--__j, *__m)) 54010b57cec5SDimitry Andric ; 54020b57cec5SDimitry Andric if (__i >= __j) 54030b57cec5SDimitry Andric break; 54040b57cec5SDimitry Andric swap(*__i, *__j); 54050b57cec5SDimitry Andric ++__n_swaps; 54060b57cec5SDimitry Andric // It is known that __m != __j 54070b57cec5SDimitry Andric // If __m just moved, follow it 54080b57cec5SDimitry Andric if (__m == __i) 54090b57cec5SDimitry Andric __m = __j; 54100b57cec5SDimitry Andric ++__i; 54110b57cec5SDimitry Andric } 54120b57cec5SDimitry Andric } 54130b57cec5SDimitry Andric // [__first, __i) < *__m and *__m <= [__i, __last) 54140b57cec5SDimitry Andric if (__i != __m && __comp(*__m, *__i)) 54150b57cec5SDimitry Andric { 54160b57cec5SDimitry Andric swap(*__i, *__m); 54170b57cec5SDimitry Andric ++__n_swaps; 54180b57cec5SDimitry Andric } 54190b57cec5SDimitry Andric // [__first, __i) < *__i and *__i <= [__i+1, __last) 54200b57cec5SDimitry Andric if (__nth == __i) 54210b57cec5SDimitry Andric return; 54220b57cec5SDimitry Andric if (__n_swaps == 0) 54230b57cec5SDimitry Andric { 54240b57cec5SDimitry Andric // We were given a perfectly partitioned sequence. Coincidence? 54250b57cec5SDimitry Andric if (__nth < __i) 54260b57cec5SDimitry Andric { 54270b57cec5SDimitry Andric // Check for [__first, __i) already sorted 54280b57cec5SDimitry Andric __j = __m = __first; 54290b57cec5SDimitry Andric while (++__j != __i) 54300b57cec5SDimitry Andric { 54310b57cec5SDimitry Andric if (__comp(*__j, *__m)) 54320b57cec5SDimitry Andric // not yet sorted, so sort 54330b57cec5SDimitry Andric goto not_sorted; 54340b57cec5SDimitry Andric __m = __j; 54350b57cec5SDimitry Andric } 54360b57cec5SDimitry Andric // [__first, __i) sorted 54370b57cec5SDimitry Andric return; 54380b57cec5SDimitry Andric } 54390b57cec5SDimitry Andric else 54400b57cec5SDimitry Andric { 54410b57cec5SDimitry Andric // Check for [__i, __last) already sorted 54420b57cec5SDimitry Andric __j = __m = __i; 54430b57cec5SDimitry Andric while (++__j != __last) 54440b57cec5SDimitry Andric { 54450b57cec5SDimitry Andric if (__comp(*__j, *__m)) 54460b57cec5SDimitry Andric // not yet sorted, so sort 54470b57cec5SDimitry Andric goto not_sorted; 54480b57cec5SDimitry Andric __m = __j; 54490b57cec5SDimitry Andric } 54500b57cec5SDimitry Andric // [__i, __last) sorted 54510b57cec5SDimitry Andric return; 54520b57cec5SDimitry Andric } 54530b57cec5SDimitry Andric } 54540b57cec5SDimitry Andricnot_sorted: 54550b57cec5SDimitry Andric // __nth_element on range containing __nth 54560b57cec5SDimitry Andric if (__nth < __i) 54570b57cec5SDimitry Andric { 5458*e8d8bef9SDimitry Andric // _VSTD::__nth_element<_Compare>(__first, __nth, __i, __comp); 54590b57cec5SDimitry Andric __last = __i; 54600b57cec5SDimitry Andric } 54610b57cec5SDimitry Andric else 54620b57cec5SDimitry Andric { 5463*e8d8bef9SDimitry Andric // _VSTD::__nth_element<_Compare>(__i+1, __nth, __last, __comp); 54640b57cec5SDimitry Andric __first = ++__i; 54650b57cec5SDimitry Andric } 54660b57cec5SDimitry Andric } 54670b57cec5SDimitry Andric} 54680b57cec5SDimitry Andric 54690b57cec5SDimitry Andrictemplate <class _RandomAccessIterator, class _Compare> 54700b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 54710b57cec5SDimitry Andricvoid 54720b57cec5SDimitry Andricnth_element(_RandomAccessIterator __first, _RandomAccessIterator __nth, _RandomAccessIterator __last, _Compare __comp) 54730b57cec5SDimitry Andric{ 54740b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5475*e8d8bef9SDimitry Andric _VSTD::__nth_element<_Comp_ref>(__first, __nth, __last, __comp); 54760b57cec5SDimitry Andric} 54770b57cec5SDimitry Andric 54780b57cec5SDimitry Andrictemplate <class _RandomAccessIterator> 54790b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY 54800b57cec5SDimitry Andricvoid 54810b57cec5SDimitry Andricnth_element(_RandomAccessIterator __first, _RandomAccessIterator __nth, _RandomAccessIterator __last) 54820b57cec5SDimitry Andric{ 54830b57cec5SDimitry Andric _VSTD::nth_element(__first, __nth, __last, __less<typename iterator_traits<_RandomAccessIterator>::value_type>()); 54840b57cec5SDimitry Andric} 54850b57cec5SDimitry Andric 54860b57cec5SDimitry Andric// includes 54870b57cec5SDimitry Andric 54880b57cec5SDimitry Andrictemplate <class _Compare, class _InputIterator1, class _InputIterator2> 54890b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 bool 54900b57cec5SDimitry Andric__includes(_InputIterator1 __first1, _InputIterator1 __last1, _InputIterator2 __first2, _InputIterator2 __last2, 54910b57cec5SDimitry Andric _Compare __comp) 54920b57cec5SDimitry Andric{ 54930b57cec5SDimitry Andric for (; __first2 != __last2; ++__first1) 54940b57cec5SDimitry Andric { 54950b57cec5SDimitry Andric if (__first1 == __last1 || __comp(*__first2, *__first1)) 54960b57cec5SDimitry Andric return false; 54970b57cec5SDimitry Andric if (!__comp(*__first1, *__first2)) 54980b57cec5SDimitry Andric ++__first2; 54990b57cec5SDimitry Andric } 55000b57cec5SDimitry Andric return true; 55010b57cec5SDimitry Andric} 55020b57cec5SDimitry Andric 55030b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _Compare> 55040b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 55050b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 55060b57cec5SDimitry Andricbool 55070b57cec5SDimitry Andricincludes(_InputIterator1 __first1, _InputIterator1 __last1, _InputIterator2 __first2, _InputIterator2 __last2, 55080b57cec5SDimitry Andric _Compare __comp) 55090b57cec5SDimitry Andric{ 55100b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5511*e8d8bef9SDimitry Andric return _VSTD::__includes<_Comp_ref>(__first1, __last1, __first2, __last2, __comp); 55120b57cec5SDimitry Andric} 55130b57cec5SDimitry Andric 55140b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2> 55150b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 55160b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 55170b57cec5SDimitry Andricbool 55180b57cec5SDimitry Andricincludes(_InputIterator1 __first1, _InputIterator1 __last1, _InputIterator2 __first2, _InputIterator2 __last2) 55190b57cec5SDimitry Andric{ 55200b57cec5SDimitry Andric return _VSTD::includes(__first1, __last1, __first2, __last2, 55210b57cec5SDimitry Andric __less<typename iterator_traits<_InputIterator1>::value_type, 55220b57cec5SDimitry Andric typename iterator_traits<_InputIterator2>::value_type>()); 55230b57cec5SDimitry Andric} 55240b57cec5SDimitry Andric 55250b57cec5SDimitry Andric// set_union 55260b57cec5SDimitry Andric 55270b57cec5SDimitry Andrictemplate <class _Compare, class _InputIterator1, class _InputIterator2, class _OutputIterator> 5528*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _OutputIterator 55290b57cec5SDimitry Andric__set_union(_InputIterator1 __first1, _InputIterator1 __last1, 55300b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result, _Compare __comp) 55310b57cec5SDimitry Andric{ 55320b57cec5SDimitry Andric for (; __first1 != __last1; ++__result) 55330b57cec5SDimitry Andric { 55340b57cec5SDimitry Andric if (__first2 == __last2) 55350b57cec5SDimitry Andric return _VSTD::copy(__first1, __last1, __result); 55360b57cec5SDimitry Andric if (__comp(*__first2, *__first1)) 55370b57cec5SDimitry Andric { 55380b57cec5SDimitry Andric *__result = *__first2; 55390b57cec5SDimitry Andric ++__first2; 55400b57cec5SDimitry Andric } 55410b57cec5SDimitry Andric else 55420b57cec5SDimitry Andric { 55430b57cec5SDimitry Andric if (!__comp(*__first1, *__first2)) 55440b57cec5SDimitry Andric ++__first2; 55450b57cec5SDimitry Andric *__result = *__first1; 55460b57cec5SDimitry Andric ++__first1; 55470b57cec5SDimitry Andric } 55480b57cec5SDimitry Andric } 55490b57cec5SDimitry Andric return _VSTD::copy(__first2, __last2, __result); 55500b57cec5SDimitry Andric} 55510b57cec5SDimitry Andric 55520b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _OutputIterator, class _Compare> 5553*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 55540b57cec5SDimitry Andric_OutputIterator 55550b57cec5SDimitry Andricset_union(_InputIterator1 __first1, _InputIterator1 __last1, 55560b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result, _Compare __comp) 55570b57cec5SDimitry Andric{ 55580b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5559*e8d8bef9SDimitry Andric return _VSTD::__set_union<_Comp_ref>(__first1, __last1, __first2, __last2, __result, __comp); 55600b57cec5SDimitry Andric} 55610b57cec5SDimitry Andric 55620b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _OutputIterator> 5563*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 55640b57cec5SDimitry Andric_OutputIterator 55650b57cec5SDimitry Andricset_union(_InputIterator1 __first1, _InputIterator1 __last1, 55660b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result) 55670b57cec5SDimitry Andric{ 55680b57cec5SDimitry Andric return _VSTD::set_union(__first1, __last1, __first2, __last2, __result, 55690b57cec5SDimitry Andric __less<typename iterator_traits<_InputIterator1>::value_type, 55700b57cec5SDimitry Andric typename iterator_traits<_InputIterator2>::value_type>()); 55710b57cec5SDimitry Andric} 55720b57cec5SDimitry Andric 55730b57cec5SDimitry Andric// set_intersection 55740b57cec5SDimitry Andric 55750b57cec5SDimitry Andrictemplate <class _Compare, class _InputIterator1, class _InputIterator2, class _OutputIterator> 55760b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _OutputIterator 55770b57cec5SDimitry Andric__set_intersection(_InputIterator1 __first1, _InputIterator1 __last1, 55780b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result, _Compare __comp) 55790b57cec5SDimitry Andric{ 55800b57cec5SDimitry Andric while (__first1 != __last1 && __first2 != __last2) 55810b57cec5SDimitry Andric { 55820b57cec5SDimitry Andric if (__comp(*__first1, *__first2)) 55830b57cec5SDimitry Andric ++__first1; 55840b57cec5SDimitry Andric else 55850b57cec5SDimitry Andric { 55860b57cec5SDimitry Andric if (!__comp(*__first2, *__first1)) 55870b57cec5SDimitry Andric { 55880b57cec5SDimitry Andric *__result = *__first1; 55890b57cec5SDimitry Andric ++__result; 55900b57cec5SDimitry Andric ++__first1; 55910b57cec5SDimitry Andric } 55920b57cec5SDimitry Andric ++__first2; 55930b57cec5SDimitry Andric } 55940b57cec5SDimitry Andric } 55950b57cec5SDimitry Andric return __result; 55960b57cec5SDimitry Andric} 55970b57cec5SDimitry Andric 55980b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _OutputIterator, class _Compare> 55990b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 56000b57cec5SDimitry Andric_OutputIterator 56010b57cec5SDimitry Andricset_intersection(_InputIterator1 __first1, _InputIterator1 __last1, 56020b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result, _Compare __comp) 56030b57cec5SDimitry Andric{ 56040b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5605*e8d8bef9SDimitry Andric return _VSTD::__set_intersection<_Comp_ref>(__first1, __last1, __first2, __last2, __result, __comp); 56060b57cec5SDimitry Andric} 56070b57cec5SDimitry Andric 56080b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _OutputIterator> 56090b57cec5SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 56100b57cec5SDimitry Andric_OutputIterator 56110b57cec5SDimitry Andricset_intersection(_InputIterator1 __first1, _InputIterator1 __last1, 56120b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result) 56130b57cec5SDimitry Andric{ 56140b57cec5SDimitry Andric return _VSTD::set_intersection(__first1, __last1, __first2, __last2, __result, 56150b57cec5SDimitry Andric __less<typename iterator_traits<_InputIterator1>::value_type, 56160b57cec5SDimitry Andric typename iterator_traits<_InputIterator2>::value_type>()); 56170b57cec5SDimitry Andric} 56180b57cec5SDimitry Andric 56190b57cec5SDimitry Andric// set_difference 56200b57cec5SDimitry Andric 56210b57cec5SDimitry Andrictemplate <class _Compare, class _InputIterator1, class _InputIterator2, class _OutputIterator> 5622*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _OutputIterator 56230b57cec5SDimitry Andric__set_difference(_InputIterator1 __first1, _InputIterator1 __last1, 56240b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result, _Compare __comp) 56250b57cec5SDimitry Andric{ 56260b57cec5SDimitry Andric while (__first1 != __last1) 56270b57cec5SDimitry Andric { 56280b57cec5SDimitry Andric if (__first2 == __last2) 56290b57cec5SDimitry Andric return _VSTD::copy(__first1, __last1, __result); 56300b57cec5SDimitry Andric if (__comp(*__first1, *__first2)) 56310b57cec5SDimitry Andric { 56320b57cec5SDimitry Andric *__result = *__first1; 56330b57cec5SDimitry Andric ++__result; 56340b57cec5SDimitry Andric ++__first1; 56350b57cec5SDimitry Andric } 56360b57cec5SDimitry Andric else 56370b57cec5SDimitry Andric { 56380b57cec5SDimitry Andric if (!__comp(*__first2, *__first1)) 56390b57cec5SDimitry Andric ++__first1; 56400b57cec5SDimitry Andric ++__first2; 56410b57cec5SDimitry Andric } 56420b57cec5SDimitry Andric } 56430b57cec5SDimitry Andric return __result; 56440b57cec5SDimitry Andric} 56450b57cec5SDimitry Andric 56460b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _OutputIterator, class _Compare> 5647*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 56480b57cec5SDimitry Andric_OutputIterator 56490b57cec5SDimitry Andricset_difference(_InputIterator1 __first1, _InputIterator1 __last1, 56500b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result, _Compare __comp) 56510b57cec5SDimitry Andric{ 56520b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5653*e8d8bef9SDimitry Andric return _VSTD::__set_difference<_Comp_ref>(__first1, __last1, __first2, __last2, __result, __comp); 56540b57cec5SDimitry Andric} 56550b57cec5SDimitry Andric 56560b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _OutputIterator> 5657*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 56580b57cec5SDimitry Andric_OutputIterator 56590b57cec5SDimitry Andricset_difference(_InputIterator1 __first1, _InputIterator1 __last1, 56600b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result) 56610b57cec5SDimitry Andric{ 56620b57cec5SDimitry Andric return _VSTD::set_difference(__first1, __last1, __first2, __last2, __result, 56630b57cec5SDimitry Andric __less<typename iterator_traits<_InputIterator1>::value_type, 56640b57cec5SDimitry Andric typename iterator_traits<_InputIterator2>::value_type>()); 56650b57cec5SDimitry Andric} 56660b57cec5SDimitry Andric 56670b57cec5SDimitry Andric// set_symmetric_difference 56680b57cec5SDimitry Andric 56690b57cec5SDimitry Andrictemplate <class _Compare, class _InputIterator1, class _InputIterator2, class _OutputIterator> 5670*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 _OutputIterator 56710b57cec5SDimitry Andric__set_symmetric_difference(_InputIterator1 __first1, _InputIterator1 __last1, 56720b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result, _Compare __comp) 56730b57cec5SDimitry Andric{ 56740b57cec5SDimitry Andric while (__first1 != __last1) 56750b57cec5SDimitry Andric { 56760b57cec5SDimitry Andric if (__first2 == __last2) 56770b57cec5SDimitry Andric return _VSTD::copy(__first1, __last1, __result); 56780b57cec5SDimitry Andric if (__comp(*__first1, *__first2)) 56790b57cec5SDimitry Andric { 56800b57cec5SDimitry Andric *__result = *__first1; 56810b57cec5SDimitry Andric ++__result; 56820b57cec5SDimitry Andric ++__first1; 56830b57cec5SDimitry Andric } 56840b57cec5SDimitry Andric else 56850b57cec5SDimitry Andric { 56860b57cec5SDimitry Andric if (__comp(*__first2, *__first1)) 56870b57cec5SDimitry Andric { 56880b57cec5SDimitry Andric *__result = *__first2; 56890b57cec5SDimitry Andric ++__result; 56900b57cec5SDimitry Andric } 56910b57cec5SDimitry Andric else 56920b57cec5SDimitry Andric ++__first1; 56930b57cec5SDimitry Andric ++__first2; 56940b57cec5SDimitry Andric } 56950b57cec5SDimitry Andric } 56960b57cec5SDimitry Andric return _VSTD::copy(__first2, __last2, __result); 56970b57cec5SDimitry Andric} 56980b57cec5SDimitry Andric 56990b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _OutputIterator, class _Compare> 5700*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 57010b57cec5SDimitry Andric_OutputIterator 57020b57cec5SDimitry Andricset_symmetric_difference(_InputIterator1 __first1, _InputIterator1 __last1, 57030b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result, _Compare __comp) 57040b57cec5SDimitry Andric{ 57050b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5706*e8d8bef9SDimitry Andric return _VSTD::__set_symmetric_difference<_Comp_ref>(__first1, __last1, __first2, __last2, __result, __comp); 57070b57cec5SDimitry Andric} 57080b57cec5SDimitry Andric 57090b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _OutputIterator> 5710*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 57110b57cec5SDimitry Andric_OutputIterator 57120b57cec5SDimitry Andricset_symmetric_difference(_InputIterator1 __first1, _InputIterator1 __last1, 57130b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _OutputIterator __result) 57140b57cec5SDimitry Andric{ 57150b57cec5SDimitry Andric return _VSTD::set_symmetric_difference(__first1, __last1, __first2, __last2, __result, 57160b57cec5SDimitry Andric __less<typename iterator_traits<_InputIterator1>::value_type, 57170b57cec5SDimitry Andric typename iterator_traits<_InputIterator2>::value_type>()); 57180b57cec5SDimitry Andric} 57190b57cec5SDimitry Andric 57200b57cec5SDimitry Andric// lexicographical_compare 57210b57cec5SDimitry Andric 57220b57cec5SDimitry Andrictemplate <class _Compare, class _InputIterator1, class _InputIterator2> 57230b57cec5SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 bool 57240b57cec5SDimitry Andric__lexicographical_compare(_InputIterator1 __first1, _InputIterator1 __last1, 57250b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _Compare __comp) 57260b57cec5SDimitry Andric{ 57270b57cec5SDimitry Andric for (; __first2 != __last2; ++__first1, (void) ++__first2) 57280b57cec5SDimitry Andric { 57290b57cec5SDimitry Andric if (__first1 == __last1 || __comp(*__first1, *__first2)) 57300b57cec5SDimitry Andric return true; 57310b57cec5SDimitry Andric if (__comp(*__first2, *__first1)) 57320b57cec5SDimitry Andric return false; 57330b57cec5SDimitry Andric } 57340b57cec5SDimitry Andric return false; 57350b57cec5SDimitry Andric} 57360b57cec5SDimitry Andric 57370b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2, class _Compare> 57380b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 57390b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 57400b57cec5SDimitry Andricbool 57410b57cec5SDimitry Andriclexicographical_compare(_InputIterator1 __first1, _InputIterator1 __last1, 57420b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2, _Compare __comp) 57430b57cec5SDimitry Andric{ 57440b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5745*e8d8bef9SDimitry Andric return _VSTD::__lexicographical_compare<_Comp_ref>(__first1, __last1, __first2, __last2, __comp); 57460b57cec5SDimitry Andric} 57470b57cec5SDimitry Andric 57480b57cec5SDimitry Andrictemplate <class _InputIterator1, class _InputIterator2> 57490b57cec5SDimitry Andric_LIBCPP_NODISCARD_EXT inline 57500b57cec5SDimitry Andric_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 57510b57cec5SDimitry Andricbool 57520b57cec5SDimitry Andriclexicographical_compare(_InputIterator1 __first1, _InputIterator1 __last1, 57530b57cec5SDimitry Andric _InputIterator2 __first2, _InputIterator2 __last2) 57540b57cec5SDimitry Andric{ 57550b57cec5SDimitry Andric return _VSTD::lexicographical_compare(__first1, __last1, __first2, __last2, 57560b57cec5SDimitry Andric __less<typename iterator_traits<_InputIterator1>::value_type, 57570b57cec5SDimitry Andric typename iterator_traits<_InputIterator2>::value_type>()); 57580b57cec5SDimitry Andric} 57590b57cec5SDimitry Andric 57600b57cec5SDimitry Andric// next_permutation 57610b57cec5SDimitry Andric 57620b57cec5SDimitry Andrictemplate <class _Compare, class _BidirectionalIterator> 5763*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 bool 57640b57cec5SDimitry Andric__next_permutation(_BidirectionalIterator __first, _BidirectionalIterator __last, _Compare __comp) 57650b57cec5SDimitry Andric{ 57660b57cec5SDimitry Andric _BidirectionalIterator __i = __last; 57670b57cec5SDimitry Andric if (__first == __last || __first == --__i) 57680b57cec5SDimitry Andric return false; 57690b57cec5SDimitry Andric while (true) 57700b57cec5SDimitry Andric { 57710b57cec5SDimitry Andric _BidirectionalIterator __ip1 = __i; 57720b57cec5SDimitry Andric if (__comp(*--__i, *__ip1)) 57730b57cec5SDimitry Andric { 57740b57cec5SDimitry Andric _BidirectionalIterator __j = __last; 57750b57cec5SDimitry Andric while (!__comp(*__i, *--__j)) 57760b57cec5SDimitry Andric ; 57770b57cec5SDimitry Andric swap(*__i, *__j); 57780b57cec5SDimitry Andric _VSTD::reverse(__ip1, __last); 57790b57cec5SDimitry Andric return true; 57800b57cec5SDimitry Andric } 57810b57cec5SDimitry Andric if (__i == __first) 57820b57cec5SDimitry Andric { 57830b57cec5SDimitry Andric _VSTD::reverse(__first, __last); 57840b57cec5SDimitry Andric return false; 57850b57cec5SDimitry Andric } 57860b57cec5SDimitry Andric } 57870b57cec5SDimitry Andric} 57880b57cec5SDimitry Andric 57890b57cec5SDimitry Andrictemplate <class _BidirectionalIterator, class _Compare> 5790*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 57910b57cec5SDimitry Andricbool 57920b57cec5SDimitry Andricnext_permutation(_BidirectionalIterator __first, _BidirectionalIterator __last, _Compare __comp) 57930b57cec5SDimitry Andric{ 57940b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5795*e8d8bef9SDimitry Andric return _VSTD::__next_permutation<_Comp_ref>(__first, __last, __comp); 57960b57cec5SDimitry Andric} 57970b57cec5SDimitry Andric 57980b57cec5SDimitry Andrictemplate <class _BidirectionalIterator> 5799*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 58000b57cec5SDimitry Andricbool 58010b57cec5SDimitry Andricnext_permutation(_BidirectionalIterator __first, _BidirectionalIterator __last) 58020b57cec5SDimitry Andric{ 58030b57cec5SDimitry Andric return _VSTD::next_permutation(__first, __last, 58040b57cec5SDimitry Andric __less<typename iterator_traits<_BidirectionalIterator>::value_type>()); 58050b57cec5SDimitry Andric} 58060b57cec5SDimitry Andric 58070b57cec5SDimitry Andric// prev_permutation 58080b57cec5SDimitry Andric 58090b57cec5SDimitry Andrictemplate <class _Compare, class _BidirectionalIterator> 5810*e8d8bef9SDimitry Andric_LIBCPP_CONSTEXPR_AFTER_CXX17 bool 58110b57cec5SDimitry Andric__prev_permutation(_BidirectionalIterator __first, _BidirectionalIterator __last, _Compare __comp) 58120b57cec5SDimitry Andric{ 58130b57cec5SDimitry Andric _BidirectionalIterator __i = __last; 58140b57cec5SDimitry Andric if (__first == __last || __first == --__i) 58150b57cec5SDimitry Andric return false; 58160b57cec5SDimitry Andric while (true) 58170b57cec5SDimitry Andric { 58180b57cec5SDimitry Andric _BidirectionalIterator __ip1 = __i; 58190b57cec5SDimitry Andric if (__comp(*__ip1, *--__i)) 58200b57cec5SDimitry Andric { 58210b57cec5SDimitry Andric _BidirectionalIterator __j = __last; 58220b57cec5SDimitry Andric while (!__comp(*--__j, *__i)) 58230b57cec5SDimitry Andric ; 58240b57cec5SDimitry Andric swap(*__i, *__j); 58250b57cec5SDimitry Andric _VSTD::reverse(__ip1, __last); 58260b57cec5SDimitry Andric return true; 58270b57cec5SDimitry Andric } 58280b57cec5SDimitry Andric if (__i == __first) 58290b57cec5SDimitry Andric { 58300b57cec5SDimitry Andric _VSTD::reverse(__first, __last); 58310b57cec5SDimitry Andric return false; 58320b57cec5SDimitry Andric } 58330b57cec5SDimitry Andric } 58340b57cec5SDimitry Andric} 58350b57cec5SDimitry Andric 58360b57cec5SDimitry Andrictemplate <class _BidirectionalIterator, class _Compare> 5837*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 58380b57cec5SDimitry Andricbool 58390b57cec5SDimitry Andricprev_permutation(_BidirectionalIterator __first, _BidirectionalIterator __last, _Compare __comp) 58400b57cec5SDimitry Andric{ 58410b57cec5SDimitry Andric typedef typename __comp_ref_type<_Compare>::type _Comp_ref; 5842*e8d8bef9SDimitry Andric return _VSTD::__prev_permutation<_Comp_ref>(__first, __last, __comp); 58430b57cec5SDimitry Andric} 58440b57cec5SDimitry Andric 58450b57cec5SDimitry Andrictemplate <class _BidirectionalIterator> 5846*e8d8bef9SDimitry Andricinline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 58470b57cec5SDimitry Andricbool 58480b57cec5SDimitry Andricprev_permutation(_BidirectionalIterator __first, _BidirectionalIterator __last) 58490b57cec5SDimitry Andric{ 58500b57cec5SDimitry Andric return _VSTD::prev_permutation(__first, __last, 58510b57cec5SDimitry Andric __less<typename iterator_traits<_BidirectionalIterator>::value_type>()); 58520b57cec5SDimitry Andric} 58530b57cec5SDimitry Andric 58540b57cec5SDimitry Andric_LIBCPP_END_NAMESPACE_STD 58550b57cec5SDimitry Andric 58560b57cec5SDimitry Andric_LIBCPP_POP_MACROS 58570b57cec5SDimitry Andric 5858e40139ffSDimitry Andric#if defined(_LIBCPP_HAS_PARALLEL_ALGORITHMS) && _LIBCPP_STD_VER >= 17 5859e40139ffSDimitry Andric# include <__pstl_algorithm> 5860e40139ffSDimitry Andric#endif 5861e40139ffSDimitry Andric 58620b57cec5SDimitry Andric#endif // _LIBCPP_ALGORITHM 5863