forked from timsort/cpp-TimSort
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathcxx_17_tests.cpp
More file actions
84 lines (69 loc) · 2.31 KB
/
cxx_17_tests.cpp
File metadata and controls
84 lines (69 loc) · 2.31 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
/*
* Copyright (c) 2011 Fuji, Goro (gfx) <gfuji@cpan.org>.
* Copyright (c) 2019 Morwenn.
*
* SPDX-License-Identifier: MIT
*/
#include <algorithm>
#include <functional>
#include <numeric>
#include <random>
#include <vector>
#include <catch2/catch.hpp>
#include <gfx/timsort.hpp>
namespace
{
struct wrapper {
wrapper() = default;
wrapper(wrapper const&) = default;
wrapper(wrapper&&) = default;
wrapper(int val) : value(val) {
}
wrapper& operator=(wrapper const&) = default;
wrapper& operator=(wrapper&&) = default;
wrapper& operator=(int val) {
value = val;
return *this;
}
bool compare_to(wrapper const& other) const {
return value < other.value;
}
int value = 0;
};
}
#ifdef __cpp_lib_invoke
TEST_CASE( "generalized callables" ) {
std::vector<wrapper> vec(50);
std::iota(vec.begin(), vec.end(), -25);
std::mt19937 gen(123456); // fixed seed is enough
std::shuffle(vec.begin(), vec.end(), gen);
const auto is_vec_sorted = [&vec] {
return std::is_sorted(vec.begin(), vec.end(), [](wrapper const& lhs, wrapper const& rhs) {
return lhs.value < rhs.value;
});
};
SECTION( "timsort for comparisons" ) {
gfx::timsort(vec, &wrapper::compare_to);
CHECK(is_vec_sorted());
}
SECTION( "timsort for projections" ) {
gfx::timsort(vec, std::less<>{}, &wrapper::value);
CHECK(is_vec_sorted());
}
std::uniform_int_distribution<int> random_middle(0, vec.size());
SECTION( "timmerge for comparisons" ) {
const auto middle = vec.begin() + random_middle(gen);
gfx::timsort(vec.begin(), middle, &wrapper::compare_to);
gfx::timsort(middle, vec.end(), &wrapper::compare_to);
gfx::timmerge(vec.begin(), middle, vec.end(), &wrapper::compare_to);
CHECK(is_vec_sorted());
}
SECTION( "timmerge for projections" ) {
const auto middle = vec.begin() + random_middle(gen);
gfx::timsort(vec.begin(), middle, std::less<>{}, &wrapper::value);
gfx::timsort(middle, vec.end(), std::less<>{}, &wrapper::value);
gfx::timmerge(vec.begin(), middle, vec.end(), std::less<>{}, &wrapper::value);
CHECK(is_vec_sorted());
}
}
#endif // __cpp_lib_invoke