Skip to content

Commit

Permalink
[libc++] [P0879] constexpr heap and partial_sort algorithms
Browse files Browse the repository at this point in the history
Now the only ones we're still missing from P0879
are `sort` and `nth_element`.

Differential Revision: https://reviews.llvm.org/D93512
  • Loading branch information
Arthur O'Dwyer committed Jan 27, 2021
1 parent bc8d8e6 commit 5386aa2
Show file tree
Hide file tree
Showing 13 changed files with 549 additions and 588 deletions.
64 changes: 32 additions & 32 deletions libcxx/include/algorithm
Expand Up @@ -367,20 +367,20 @@ template <class RandomAccessIterator, class Compare>
stable_sort(RandomAccessIterator first, RandomAccessIterator last, Compare comp);
template <class RandomAccessIterator>
void
constexpr void // constexpr in C++20
partial_sort(RandomAccessIterator first, RandomAccessIterator middle, RandomAccessIterator last);
template <class RandomAccessIterator, class Compare>
void
constexpr void // constexpr in C++20
partial_sort(RandomAccessIterator first, RandomAccessIterator middle, RandomAccessIterator last, Compare comp);
template <class InputIterator, class RandomAccessIterator>
RandomAccessIterator
constexpr RandomAccessIterator // constexpr in C++20
partial_sort_copy(InputIterator first, InputIterator last,
RandomAccessIterator result_first, RandomAccessIterator result_last);
template <class InputIterator, class RandomAccessIterator, class Compare>
RandomAccessIterator
constexpr RandomAccessIterator // constexpr in C++20
partial_sort_copy(InputIterator first, InputIterator last,
RandomAccessIterator result_first, RandomAccessIterator result_last, Compare comp);
Expand Down Expand Up @@ -491,35 +491,35 @@ template <class InputIterator1, class InputIterator2, class OutputIterator, clas
InputIterator2 first2, InputIterator2 last2, OutputIterator result, Compare comp);
template <class RandomAccessIterator>
void
constexpr void // constexpr in C++20
push_heap(RandomAccessIterator first, RandomAccessIterator last);
template <class RandomAccessIterator, class Compare>
void
constexpr void // constexpr in C++20
push_heap(RandomAccessIterator first, RandomAccessIterator last, Compare comp);
template <class RandomAccessIterator>
void
constexpr void // constexpr in C++20
pop_heap(RandomAccessIterator first, RandomAccessIterator last);
template <class RandomAccessIterator, class Compare>
void
constexpr void // constexpr in C++20
pop_heap(RandomAccessIterator first, RandomAccessIterator last, Compare comp);
template <class RandomAccessIterator>
void
constexpr void // constexpr in C++20
make_heap(RandomAccessIterator first, RandomAccessIterator last);
template <class RandomAccessIterator, class Compare>
void
constexpr void // constexpr in C++20
make_heap(RandomAccessIterator first, RandomAccessIterator last, Compare comp);
template <class RandomAccessIterator>
void
constexpr void // constexpr in C++20
sort_heap(RandomAccessIterator first, RandomAccessIterator last);
template <class RandomAccessIterator, class Compare>
void
constexpr void // constexpr in C++20
sort_heap(RandomAccessIterator first, RandomAccessIterator last, Compare comp);
template <class RandomAccessIterator>
Expand Down Expand Up @@ -5000,7 +5000,7 @@ is_heap(_RandomAccessIterator __first, _RandomAccessIterator __last)
// push_heap

template <class _Compare, class _RandomAccessIterator>
void
_LIBCPP_CONSTEXPR_AFTER_CXX11 void
__sift_up(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp,
typename iterator_traits<_RandomAccessIterator>::difference_type __len)
{
Expand All @@ -5027,7 +5027,7 @@ __sift_up(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare
}

template <class _RandomAccessIterator, class _Compare>
inline _LIBCPP_INLINE_VISIBILITY
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
void
push_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp)
{
Expand All @@ -5036,7 +5036,7 @@ push_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare
}

template <class _RandomAccessIterator>
inline _LIBCPP_INLINE_VISIBILITY
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
void
push_heap(_RandomAccessIterator __first, _RandomAccessIterator __last)
{
Expand All @@ -5046,7 +5046,7 @@ push_heap(_RandomAccessIterator __first, _RandomAccessIterator __last)
// pop_heap

template <class _Compare, class _RandomAccessIterator>
void
_LIBCPP_CONSTEXPR_AFTER_CXX11 void
__sift_down(_RandomAccessIterator __first, _RandomAccessIterator /*__last*/,
_Compare __comp,
typename iterator_traits<_RandomAccessIterator>::difference_type __len,
Expand Down Expand Up @@ -5078,7 +5078,7 @@ __sift_down(_RandomAccessIterator __first, _RandomAccessIterator /*__last*/,
value_type __top(_VSTD::move(*__start));
do
{
// we are not in heap-order, swap the parent with it's largest child
// we are not in heap-order, swap the parent with its largest child
*__start = _VSTD::move(*__child_i);
__start = __child_i;

Expand All @@ -5101,7 +5101,7 @@ __sift_down(_RandomAccessIterator __first, _RandomAccessIterator /*__last*/,
}

template <class _Compare, class _RandomAccessIterator>
inline _LIBCPP_INLINE_VISIBILITY
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
void
__pop_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp,
typename iterator_traits<_RandomAccessIterator>::difference_type __len)
Expand All @@ -5114,7 +5114,7 @@ __pop_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare
}

template <class _RandomAccessIterator, class _Compare>
inline _LIBCPP_INLINE_VISIBILITY
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
void
pop_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp)
{
Expand All @@ -5123,7 +5123,7 @@ pop_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare _
}

template <class _RandomAccessIterator>
inline _LIBCPP_INLINE_VISIBILITY
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
void
pop_heap(_RandomAccessIterator __first, _RandomAccessIterator __last)
{
Expand All @@ -5133,7 +5133,7 @@ pop_heap(_RandomAccessIterator __first, _RandomAccessIterator __last)
// make_heap

template <class _Compare, class _RandomAccessIterator>
void
_LIBCPP_CONSTEXPR_AFTER_CXX11 void
__make_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp)
{
typedef typename iterator_traits<_RandomAccessIterator>::difference_type difference_type;
Expand All @@ -5149,7 +5149,7 @@ __make_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compar
}

template <class _RandomAccessIterator, class _Compare>
inline _LIBCPP_INLINE_VISIBILITY
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
void
make_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp)
{
Expand All @@ -5158,7 +5158,7 @@ make_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare
}

template <class _RandomAccessIterator>
inline _LIBCPP_INLINE_VISIBILITY
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
void
make_heap(_RandomAccessIterator __first, _RandomAccessIterator __last)
{
Expand All @@ -5168,7 +5168,7 @@ make_heap(_RandomAccessIterator __first, _RandomAccessIterator __last)
// sort_heap

template <class _Compare, class _RandomAccessIterator>
void
_LIBCPP_CONSTEXPR_AFTER_CXX17 void
__sort_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp)
{
typedef typename iterator_traits<_RandomAccessIterator>::difference_type difference_type;
Expand All @@ -5177,7 +5177,7 @@ __sort_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compar
}

template <class _RandomAccessIterator, class _Compare>
inline _LIBCPP_INLINE_VISIBILITY
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
void
sort_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp)
{
Expand All @@ -5186,7 +5186,7 @@ sort_heap(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare
}

template <class _RandomAccessIterator>
inline _LIBCPP_INLINE_VISIBILITY
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
void
sort_heap(_RandomAccessIterator __first, _RandomAccessIterator __last)
{
Expand All @@ -5196,7 +5196,7 @@ sort_heap(_RandomAccessIterator __first, _RandomAccessIterator __last)
// partial_sort

template <class _Compare, class _RandomAccessIterator>
void
_LIBCPP_CONSTEXPR_AFTER_CXX17 void
__partial_sort(_RandomAccessIterator __first, _RandomAccessIterator __middle, _RandomAccessIterator __last,
_Compare __comp)
{
Expand All @@ -5214,7 +5214,7 @@ __partial_sort(_RandomAccessIterator __first, _RandomAccessIterator __middle, _R
}

template <class _RandomAccessIterator, class _Compare>
inline _LIBCPP_INLINE_VISIBILITY
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
void
partial_sort(_RandomAccessIterator __first, _RandomAccessIterator __middle, _RandomAccessIterator __last,
_Compare __comp)
Expand All @@ -5224,7 +5224,7 @@ partial_sort(_RandomAccessIterator __first, _RandomAccessIterator __middle, _Ran
}

template <class _RandomAccessIterator>
inline _LIBCPP_INLINE_VISIBILITY
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
void
partial_sort(_RandomAccessIterator __first, _RandomAccessIterator __middle, _RandomAccessIterator __last)
{
Expand All @@ -5235,7 +5235,7 @@ partial_sort(_RandomAccessIterator __first, _RandomAccessIterator __middle, _Ran
// partial_sort_copy

template <class _Compare, class _InputIterator, class _RandomAccessIterator>
_RandomAccessIterator
_LIBCPP_CONSTEXPR_AFTER_CXX17 _RandomAccessIterator
__partial_sort_copy(_InputIterator __first, _InputIterator __last,
_RandomAccessIterator __result_first, _RandomAccessIterator __result_last, _Compare __comp)
{
Expand All @@ -5258,7 +5258,7 @@ __partial_sort_copy(_InputIterator __first, _InputIterator __last,
}

template <class _InputIterator, class _RandomAccessIterator, class _Compare>
inline _LIBCPP_INLINE_VISIBILITY
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
_RandomAccessIterator
partial_sort_copy(_InputIterator __first, _InputIterator __last,
_RandomAccessIterator __result_first, _RandomAccessIterator __result_last, _Compare __comp)
Expand All @@ -5268,7 +5268,7 @@ partial_sort_copy(_InputIterator __first, _InputIterator __last,
}

template <class _InputIterator, class _RandomAccessIterator>
inline _LIBCPP_INLINE_VISIBILITY
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
_RandomAccessIterator
partial_sort_copy(_InputIterator __first, _InputIterator __last,
_RandomAccessIterator __result_first, _RandomAccessIterator __result_last)
Expand Down
Expand Up @@ -10,43 +10,57 @@

// template<RandomAccessIterator Iter>
// requires ShuffleIterator<Iter> && LessThanComparable<Iter::value_type>
// void
// constexpr void // constexpr in C++20
// make_heap(Iter first, Iter last);

#include <algorithm>
#include <random>
#include <cassert>

#include "test_macros.h"
#include "test_iterators.h"
#include "MoveOnly.h"

std::mt19937 randomness;

void test(int N)
template<class T, class Iter>
TEST_CONSTEXPR_CXX20 bool test()
{
int* ia = new int [N];
for (int i = 0; i < N; ++i)
ia[i] = i;
std::shuffle(ia, ia+N, randomness);
std::make_heap(ia, ia+N);
assert(std::is_heap(ia, ia+N));

typedef random_access_iterator<int *> RI;
std::shuffle(RI(ia), RI(ia+N), randomness);
std::make_heap(RI(ia), RI(ia+N));
assert(std::is_heap(RI(ia), RI(ia+N)));

delete [] ia;
int orig[15] = {3,1,4,1,5, 9,2,6,5,3, 5,8,9,7,9};
T work[15] = {3,1,4,1,5, 9,2,6,5,3, 5,8,9,7,9};
for (int n = 0; n < 15; ++n) {
std::make_heap(Iter(work), Iter(work+n));
assert(std::is_heap(work, work+n));
assert(std::is_permutation(work, work+n, orig));
std::copy(orig, orig+n, work);
}

{
T input[] = {3, 4, 1, 2, 5};
std::make_heap(Iter(input), Iter(input + 5));
assert(std::is_heap(input, input + 5));
std::pop_heap(input, input + 5); assert(input[4] == 5);
std::pop_heap(input, input + 4); assert(input[3] == 4);
std::pop_heap(input, input + 3); assert(input[2] == 3);
std::pop_heap(input, input + 2); assert(input[1] == 2);
std::pop_heap(input, input + 1); assert(input[0] == 1);
}
return true;
}

int main(int, char**)
{
test(0);
test(1);
test(2);
test(3);
test(10);
test(1000);

return 0;
test<int, random_access_iterator<int*> >();
test<int, int*>();

#if TEST_STD_VER >= 11
test<MoveOnly, random_access_iterator<MoveOnly*>>();
test<MoveOnly, MoveOnly*>();
#endif

#if TEST_STD_VER >= 20
static_assert(test<int, random_access_iterator<int*>>());
static_assert(test<int, int*>());
static_assert(test<MoveOnly, random_access_iterator<MoveOnly*>>());
static_assert(test<MoveOnly, MoveOnly*>());
#endif

return 0;
}

0 comments on commit 5386aa2

Please sign in to comment.