void test_iter_comp(Iter first, Sent last) { Iter i = stl2::max_element(first, last, std::greater<int>()); if (first != last) { for (Iter j = first; j != last; ++j) CHECK(!std::greater<int>()(*i, *j)); } else CHECK(i == last); auto rng = stl2::ext::make_range(first, last); i = stl2::max_element(rng, std::greater<int>()); if (first != last) { for (Iter j = first; j != last; ++j) CHECK(!std::greater<int>()(*i, *j)); } else CHECK(i == last); auto res = stl2::max_element(std::move(rng), std::greater<int>()); if (first != last) { for (Iter j = first; j != last; ++j) CHECK(!std::greater<int>()(*res.get_unsafe(), *j)); } else CHECK(res.get_unsafe() == last); }
void test_iter(Iter first, Sent last) { Iter i = stl2::max_element(first, last); if (first != last) { for (Iter j = first; j != last; ++j) CHECK(!(*i < *j)); } else CHECK(i == last); auto rng = stl2::ext::make_range(first, last); i = stl2::max_element(rng); if (first != last) { for (Iter j = first; j != last; ++j) CHECK(!(*i < *j)); } else CHECK(i == last); auto j = stl2::max_element(std::move(rng)); if (first != last) { for (Iter k = first; k != last; ++k) CHECK(!(*j.get_unsafe() < *k)); } else CHECK(j.get_unsafe() == last); }
void test_iter_comp(Iter first, Sent last) { typedef std::greater<int> Compare; Compare comp; std::pair<Iter, Iter> p = ranges::minmax_element(first, last, comp); if (first != last) { for (Iter j = first; j != last; ++j) { CHECK(!comp(*j, *p.first)); CHECK(!comp(*p.second, *j)); } } else { CHECK(p.first == last); CHECK(p.second == last); } auto rng = ranges::make_range(first, last); p = ranges::minmax_element(rng, comp); if (first != last) { for (Iter j = first; j != last; ++j) { CHECK(!comp(*j, *p.first)); CHECK(!comp(*p.second, *j)); } } else { CHECK(p.first == last); CHECK(p.second == last); } auto res = ranges::minmax_element(std::move(rng), comp); if (first != last) { for (Iter j = first; j != last; ++j) { CHECK(!comp(*j, *res.get_unsafe().first)); CHECK(!comp(*res.get_unsafe().second, *j)); } } else { CHECK(res.get_unsafe().first == last); CHECK(res.get_unsafe().second == last); } }
void test_iter(Iter first, Sent last) { std::pair<Iter, Iter> p = ranges::minmax_element(first, last); if (first != last) { for (Iter j = first; j != last; ++j) { CHECK(!(*j < *p.first)); CHECK(!(*p.second < *j)); } } else { CHECK(p.first == last); CHECK(p.second == last); } auto rng = ranges::make_range(first, last); p = ranges::minmax_element(rng); if (first != last) { for (Iter j = first; j != last; ++j) { CHECK(!(*j < *p.first)); CHECK(!(*p.second < *j)); } } else { CHECK(p.first == last); CHECK(p.second == last); } auto res = ranges::minmax_element(std::move(rng)); if (first != last) { for (Iter j = first; j != last; ++j) { CHECK(!(*j < *res.get_unsafe().first)); CHECK(!(*p.second < *j)); } } else { CHECK(res.get_unsafe().first == last); CHECK(res.get_unsafe().second == last); } }
void test_one_rng(unsigned N, unsigned M) { assert(M <= N); int* ia = new int[N]; for (unsigned i = 0; i < N; ++i) ia[i] = i; std::random_shuffle(ia, ia+N); std::sort(ia, ia+M); std::sort(ia+M, ia+N); auto res = ranges::inplace_merge(::as_lvalue(ranges::make_range(Iter(ia), Sent(ia+N))), Iter(ia+M)); CHECK(res == Iter(ia+N)); if(N > 0) { CHECK(ia[0] == 0); CHECK(ia[N-1] == (int)N-1); CHECK(std::is_sorted(ia, ia+N)); } std::random_shuffle(ia, ia+N); std::sort(ia, ia+M); std::sort(ia+M, ia+N); auto res2 = ranges::inplace_merge(ranges::make_range(Iter(ia), Sent(ia+N)), Iter(ia+M)); CHECK(res2.get_unsafe() == Iter(ia+N)); if(N > 0) { CHECK(ia[0] == 0); CHECK(ia[N-1] == (int)N-1); CHECK(std::is_sorted(ia, ia+N)); } delete [] ia; }
int main() { test_iter<forward_iterator<int*> >(); test_iter<bidirectional_iterator<int*> >(); test_iter<random_access_iterator<int*> >(); test_iter<int*>(); test_iter<forward_iterator<int*>, sentinel<int*>>(); test_iter<bidirectional_iterator<int*>, sentinel<int*>>(); test_iter<random_access_iterator<int*>, sentinel<int*>>(); test_range<forward_iterator<int*> >(); test_range<bidirectional_iterator<int*> >(); test_range<random_access_iterator<int*> >(); test_range<int*>(); test_range<forward_iterator<int*>, sentinel<int*>>(); test_range<bidirectional_iterator<int*>, sentinel<int*>>(); test_range<random_access_iterator<int*>, sentinel<int*>>(); test_iter_rvalue<forward_iterator<std::unique_ptr<int>*> >(); test_iter_rvalue<bidirectional_iterator<std::unique_ptr<int>*> >(); test_iter_rvalue<random_access_iterator<std::unique_ptr<int>*> >(); test_iter_rvalue<std::unique_ptr<int>*>(); test_iter_rvalue<forward_iterator<std::unique_ptr<int>*>, sentinel<std::unique_ptr<int>*>>(); test_iter_rvalue<bidirectional_iterator<std::unique_ptr<int>*>, sentinel<std::unique_ptr<int>*>>(); test_iter_rvalue<random_access_iterator<std::unique_ptr<int>*>, sentinel<std::unique_ptr<int>*>>(); test_range_rvalue<forward_iterator<std::unique_ptr<int>*> >(); test_range_rvalue<bidirectional_iterator<std::unique_ptr<int>*> >(); test_range_rvalue<random_access_iterator<std::unique_ptr<int>*> >(); test_range_rvalue<std::unique_ptr<int>*>(); test_range_rvalue<forward_iterator<std::unique_ptr<int>*>, sentinel<std::unique_ptr<int>*>>(); test_range_rvalue<bidirectional_iterator<std::unique_ptr<int>*>, sentinel<std::unique_ptr<int>*>>(); test_range_rvalue<random_access_iterator<std::unique_ptr<int>*>, sentinel<std::unique_ptr<int>*>>(); // Check projection S ia[] = {S{0}, S{1}, S{2}, S{3}, S{4}, S{2}, S{3}, S{4}, S{2}}; constexpr unsigned sa = stl2::size(ia); S* r = stl2::remove(ia, 2, &S::i); CHECK(r == ia + sa-3); CHECK(ia[0].i == 0); CHECK(ia[1].i == 1); CHECK(ia[2].i == 3); CHECK(ia[3].i == 4); CHECK(ia[4].i == 3); CHECK(ia[5].i == 4); // Check rvalue range S ia2[] = {S{0}, S{1}, S{2}, S{3}, S{4}, S{2}, S{3}, S{4}, S{2}}; constexpr unsigned sa2 = stl2::size(ia2); auto r2 = stl2::remove(stl2::move(ia2), 2, &S::i); CHECK(r2.get_unsafe() == ia2 + sa2-3); CHECK(ia2[0].i == 0); CHECK(ia2[1].i == 1); CHECK(ia2[2].i == 3); CHECK(ia2[3].i == 4); CHECK(ia2[4].i == 3); CHECK(ia2[5].i == 4); return ::test_result(); }
void test_char() { const unsigned n = 4; char ca[n] = {0}; auto i = ranges::fill(Iter(ca), Sent(ca+n), char(1)); CHECK(ca[0] == 1); CHECK(ca[1] == 1); CHECK(ca[2] == 1); CHECK(ca[3] == 1); CHECK(i == Iter(ca + 4)); auto rng = ranges::make_iterator_range(Iter(ca), Sent(ca+n)); i = ranges::fill(rng, char(2)); CHECK(ca[0] == 2); CHECK(ca[1] == 2); CHECK(ca[2] == 2); CHECK(ca[3] == 2); CHECK(i == Iter(ca + 4)); auto j = ranges::fill(ranges::make_iterator_range(Iter(ca), Sent(ca+n)), char(3)); CHECK(ca[0] == 3); CHECK(ca[1] == 3); CHECK(ca[2] == 3); CHECK(ca[3] == 3); CHECK(j.get_unsafe() == Iter(ca + 4)); }
void test_char() { const unsigned n = 4; char ca[n] = {0}; auto i = count_and_fill(Iter(ca), Sent(ca+n), char(1)); CHECK(ca[0] == 1); CHECK(ca[1] == 1); CHECK(ca[2] == 1); CHECK(ca[3] == 1); CHECK(i == Iter(ca + 4)); auto rng = stl2::ext::make_range(Iter(ca), Sent(ca+n)); i = count_and_fill(rng, char(2)); CHECK(ca[0] == 2); CHECK(ca[1] == 2); CHECK(ca[2] == 2); CHECK(ca[3] == 2); CHECK(i == Iter(ca + 4)); auto j = count_and_fill(stl2::ext::make_range(Iter(ca), Sent(ca+n)), char(3)); CHECK(ca[0] == 3); CHECK(ca[1] == 3); CHECK(ca[2] == 3); CHECK(ca[3] == 3); CHECK(j.get_unsafe() == Iter(ca + 4)); }
static inline void clear_item(iq_t iq, seqno_t i) { item_t *item = get_unsafe(iq, i) ; if (!item->msg) { return ; } iq->free(item->msg) ; item->msg = NULL ; }
iq_item_t get_msg(iq_t iq, seqno_t i) { item_t *item ; assert(i >= iq->lo) ; if (i >= maxi(iq)) { return NULL ; } item = get_unsafe(iq, i) ; return item->msg ; }
bool_t iq_read_prefix(iq_t iq, seqno_t *seqno, iq_item_t *msg) { seqno_t read = iq->read ; item_t *item ; if (!get_msg(iq, read)) { return FALSE ; } item = get_unsafe(iq, read) ; *msg = item->msg ; *seqno = read ; iq->read = read + 1 ; return TRUE ; }
int main() { test_iter<forward_iterator<int*> >(); test_iter<bidirectional_iterator<int*> >(); test_iter<random_access_iterator<int*> >(); test_iter<int*>(); test_iter<forward_iterator<int*>, sentinel<int*> >(); test_iter<bidirectional_iterator<int*>, sentinel<int*> >(); test_iter<random_access_iterator<int*>, sentinel<int*> >(); test_range<forward_iterator<int*> >(); test_range<bidirectional_iterator<int*> >(); test_range<random_access_iterator<int*> >(); test_range<int*>(); test_range<forward_iterator<int*>, sentinel<int*> >(); test_range<bidirectional_iterator<int*>, sentinel<int*> >(); test_range<random_access_iterator<int*>, sentinel<int*> >(); // Test projections S ia[] = {S{1}, S{2}, S{3}, S{4}, S{5}, S{6}, S{7}, S{8} ,S{9}}; const unsigned sa = sizeof(ia)/sizeof(ia[0]); S* r = ranges::partition(ia, is_odd(), &S::i); CHECK(r == ia + 5); for (S* i = ia; i < r; ++i) CHECK(is_odd()(i->i)); for (S* i = r; i < ia+sa; ++i) CHECK(!is_odd()(i->i)); // Test rvalue range auto r2 = ranges::partition(ranges::view::all(ia), is_odd(), &S::i); CHECK(r2.get_unsafe() == ia + 5); for (S* i = ia; i < r2.get_unsafe(); ++i) CHECK(is_odd()(i->i)); for (S* i = r2.get_unsafe(); i < ia+sa; ++i) CHECK(!is_odd()(i->i)); return ::test_result(); }
void iq_opt_insert_doread(iq_t iq, seqno_t i, iq_item_t msg) { item_t *item ; seqno_t next ; assert(iq_opt_insert_check(iq, i)) ; assert (i >= iq->lo) ; next = i + 1 ; iq->read = next ; iq->hi = next ; if (i >= maxi(iq)) { overflow(iq, i) ; } item = get_unsafe(iq, i) ; do_set(item, msg) ; }
int main() { test_iter<forward_iterator<int*> >(); test_iter<bidirectional_iterator<int*> >(); test_iter<random_access_iterator<int*> >(); test_iter<int*>(); test_iter<forward_iterator<int*>, sentinel<int*> >(); test_iter<bidirectional_iterator<int*>, sentinel<int*> >(); test_iter<random_access_iterator<int*>, sentinel<int*> >(); test_rng<forward_iterator<int*> >(); test_rng<bidirectional_iterator<int*> >(); test_rng<random_access_iterator<int*> >(); test_rng<int*>(); test_rng<forward_iterator<int*>, sentinel<int*> >(); test_rng<bidirectional_iterator<int*>, sentinel<int*> >(); test_rng<random_access_iterator<int*>, sentinel<int*> >(); // test projection { using P = std::pair<int,std::string>; P ia[] = {{0,"0"}, {1,"1"}, {2,"2"}, {3,"3"}, {4,"4"}}; P *i = ranges::replace_if(ia, [](int i){return i==2;}, std::make_pair(42,"42"), &std::pair<int,std::string>::first); CHECK(ia[0] == P{0,"0"}); CHECK(ia[1] == P{1,"1"}); CHECK(ia[2] == P{42,"42"}); CHECK(ia[3] == P{3,"3"}); CHECK(ia[4] == P{4,"4"}); CHECK(i == ranges::end(ia)); } // test rvalue range { using P = std::pair<int,std::string>; P ia[] = {{0,"0"}, {1,"1"}, {2,"2"}, {3,"3"}, {4,"4"}}; auto i = ranges::replace_if(ranges::view::all(ia), [](int i){return i==2;}, std::make_pair(42,"42"), &std::pair<int,std::string>::first); CHECK(ia[0] == P{0,"0"}); CHECK(ia[1] == P{1,"1"}); CHECK(ia[2] == P{42,"42"}); CHECK(ia[3] == P{3,"3"}); CHECK(ia[4] == P{4,"4"}); CHECK(i.get_unsafe() == ranges::end(ia)); } return ::test_result(); }
iq_status_t iq_get(iq_t iq, seqno_t i, iq_item_t *msg) { assert(msg) ; if (i < iq->lo) { return IQ_RESET ; } else if (i >= maxi(iq)) { return IQ_UNSET ; } else { item_t *item = get_unsafe(iq, i) ; if (!item->msg) { return IQ_UNSET ; } *msg = item->msg ; return IQ_DATA ; } }
static inline bool_t set(iq_t iq, seqno_t i, iq_item_t msg) { item_t *item ; assert(msg) ; if (i < iq->lo) { return FALSE ; } iq_set_hi(iq, i + 1) ; if (i >= maxi(iq)) { overflow(iq, i) ; } item = get_unsafe(iq, i) ; if (item->msg) { return FALSE ; } do_set(item, msg) ; return TRUE ; }
bool_t iq_get_prefix(iq_t iq, seqno_t *seqno, iq_item_t *msg) { seqno_t lo = iq->lo ; item_t *item ; if (!get_msg(iq, lo)) { return FALSE ; } item = get_unsafe(iq, lo) ; *msg = item->msg ; *seqno = lo ; /* Watch out! The iq_set_lo will try to zap this * item. */ item->msg = NULL ; iq_set_lo(iq, (lo + 1)) ; return TRUE ; }
void test_larger_sorts(int N, int M) { assert(N > 0); assert(M >= 0 && M <= N); int* array = new int[N]; for(int i = 0; i < N; ++i) array[i] = i; using I = random_access_iterator<int*>; using S = sentinel<int*>; std::shuffle(array, array+N, gen); int *res = ranges::partial_sort(array, array+M, array+N); CHECK(res == array+N); for(int i = 0; i < M; ++i) CHECK(array[i] == i); std::shuffle(array, array+N, gen); I res2 = ranges::partial_sort(I{array}, I{array+M}, S{array+N}); CHECK(res2.base() == array+N); for(int i = 0; i < M; ++i) CHECK(array[i] == i); std::shuffle(array, array+N, gen); res = ranges::partial_sort(::as_lvalue(ranges::make_range(array, array+N)), array+M); CHECK(res == array+N); for(int i = 0; i < M; ++i) CHECK(array[i] == i); std::shuffle(array, array+N, gen); res2 = ranges::partial_sort(::as_lvalue(ranges::make_range(I{array}, S{array+N})), I{array+M}); CHECK(res2.base() == array+N); for(int i = 0; i < M; ++i) CHECK(array[i] == i); std::shuffle(array, array+N, gen); auto res3 = ranges::partial_sort(ranges::make_range(array, array+N), array+M); CHECK(res3.get_unsafe() == array+N); for(int i = 0; i < M; ++i) CHECK(array[i] == i); std::shuffle(array, array+N, gen); auto res4 = ranges::partial_sort(ranges::make_range(I{array}, S{array+N}), I{array+M}); CHECK(res4.get_unsafe().base() == array+N); for(int i = 0; i < M; ++i) CHECK(array[i] == i); std::shuffle(array, array+N, gen); res = ranges::partial_sort(array, array+M, array+N, std::greater<int>()); CHECK(res == array+N); for(int i = 0; i < M; ++i) CHECK(array[i] == N-i-1); std::shuffle(array, array+N, gen); res2 = ranges::partial_sort(I{array}, I{array+M}, S{array+N}, std::greater<int>()); CHECK(res2.base() == array+N); for(int i = 0; i < M; ++i) CHECK(array[i] == N-i-1); std::shuffle(array, array+N, gen); res = ranges::partial_sort(::as_lvalue(ranges::make_range(array, array+N)), array+M, std::greater<int>()); CHECK(res == array+N); for(int i = 0; i < M; ++i) CHECK(array[i] == N-i-1); std::shuffle(array, array+N, gen); res2 = ranges::partial_sort(::as_lvalue(ranges::make_range(I{array}, S{array+N})), I{array+M}, std::greater<int>()); CHECK(res2.base() == array+N); for(int i = 0; i < M; ++i) CHECK(array[i] == N-i-1); delete [] array; }
int main() { int i = 0; int * r = ranges::partial_sort_copy(&i, &i, &i, &i+5); CHECK(r == &i); CHECK(i == 0); test<input_iterator<const int*> >(); test<forward_iterator<const int*> >(); test<bidirectional_iterator<const int*> >(); test<random_access_iterator<const int*> >(); test<const int*>(); // Check projections { constexpr int N = 256; constexpr int M = N/2-1; S input[N]; U output[M]; for (int i = 0; i < N; ++i) input[i].i = i; std::random_shuffle(input, input+N); U * r = ranges::partial_sort_copy(input, output, std::less<int>(), &S::i, &U::i); U* e = output + std::min(N, M); CHECK(r == e); int i = 0; for (U* x = output; x < e; ++x, ++i) CHECK(x->i == i); } // Check rvalue ranges { constexpr int N = 256; constexpr int M = N/2-1; S input[N]; U output[M]; for (int i = 0; i < N; ++i) input[i].i = i; std::random_shuffle(input, input+N); auto r = ranges::partial_sort_copy(input, ranges::view::all(output), std::less<int>(), &S::i, &U::i); U* e = output + std::min(N, M); CHECK(r.get_unsafe() == e); int i = 0; for (U* x = output; x < e; ++x, ++i) CHECK(x->i == i); } // Check initialize_list { U output[9]; U * r = ranges::partial_sort_copy( {S{5}, S{3}, S{4}, S{1}, S{8}, S{2}, S{6}, S{7}, S{0}, S{9}}, output, std::less<int>(), &S::i, &U::i); U* e = output + 9; CHECK(r == e); int i = 0; for (U* x = output; x < e; ++x, ++i) CHECK(x->i == i); } return ::test_result(); }