1 | // |
2 | // immer: immutable data structures for C++ |
3 | // Copyright (C) 2016, 2017, 2018 Juan Pedro Bolivar Puente |
4 | // |
5 | // This software is distributed under the Boost Software License, Version 1.0. |
6 | // See accompanying file LICENSE or copy at http://boost.org/LICENSE_1_0.txt |
7 | // |
8 | |
9 | #include <immer/detail/type_traits.hpp> |
10 | #include <forward_list> |
11 | #include <list> |
12 | #include <vector> |
13 | #include <catch.hpp> |
14 | |
15 | struct string_sentinel {}; |
16 | bool operator==(const char* i, string_sentinel); |
17 | bool operator!=(const char* i, string_sentinel); |
18 | |
19 | TEST_CASE("compatible_sentinel_v" ) |
20 | { |
21 | SECTION("iterator pairs" ) |
22 | { |
23 | using Iter = std::vector<int>::iterator; |
24 | static_assert(immer::detail::compatible_sentinel_v<Iter, Iter>, "" ); |
25 | } |
26 | |
27 | SECTION("pointer pairs" ) |
28 | { |
29 | using Iter = char*; |
30 | static_assert(immer::detail::compatible_sentinel_v<Iter, Iter>, "" ); |
31 | } |
32 | |
33 | SECTION("iterator/sentinel pair" ) |
34 | { |
35 | using Iter = char*; |
36 | using Sent = string_sentinel; |
37 | static_assert(immer::detail::compatible_sentinel_v<Iter, Sent>, "" ); |
38 | } |
39 | |
40 | SECTION("incompatible pair" ) |
41 | { |
42 | using Iter1 = std::vector<int>::iterator; |
43 | using Iter2 = std::list<double>::iterator; |
44 | static_assert(not immer::detail::compatible_sentinel_v<Iter1, Iter2>, "" ); |
45 | } |
46 | } |
47 | |
48 | TEST_CASE("equality comparable" ) |
49 | { |
50 | SECTION("iterator pairs" ) |
51 | { |
52 | using Iter = std::vector<int>::iterator; |
53 | static_assert(immer::detail::is_equality_comparable_v<Iter, Iter>, "" ); |
54 | } |
55 | |
56 | SECTION("pointer pairs" ) |
57 | { |
58 | using Iter = char*; |
59 | static_assert(immer::detail::is_equality_comparable_v<Iter, Iter>, "" ); |
60 | } |
61 | |
62 | SECTION("iterator/sentinel pair" ) |
63 | { |
64 | using Iter = char*; |
65 | using Sent = string_sentinel; |
66 | static_assert(immer::detail::is_equality_comparable_v<Iter, Sent>, "" ); |
67 | } |
68 | |
69 | SECTION("not equality comparable" ) |
70 | { |
71 | static_assert(not immer::detail::is_equality_comparable_v<std::string, double>, "" ); |
72 | } |
73 | } |
74 | |
75 | TEST_CASE("inequality comparable" ) |
76 | { |
77 | SECTION("iterator pairs" ) |
78 | { |
79 | using Iter = std::vector<int>::iterator; |
80 | static_assert(immer::detail::is_inequality_comparable_v<Iter, Iter>, "" ); |
81 | } |
82 | |
83 | SECTION("pointer pairs" ) |
84 | { |
85 | using Iter = char*; |
86 | static_assert(immer::detail::is_inequality_comparable_v<Iter, Iter>, "" ); |
87 | } |
88 | |
89 | SECTION("iterator/sentinel pair" ) |
90 | { |
91 | using Iter = char*; |
92 | using Sent = string_sentinel; |
93 | static_assert(immer::detail::is_inequality_comparable_v<Iter, Sent>, "" ); |
94 | } |
95 | |
96 | SECTION("not inequality comparable" ) |
97 | { |
98 | static_assert(not immer::detail::is_inequality_comparable_v<std::string, double>, "" ); |
99 | } |
100 | } |
101 | |
102 | TEST_CASE("is dereferenceable" ) |
103 | { |
104 | SECTION("iterator" ) |
105 | { |
106 | using Iter = std::vector<int>::iterator; |
107 | static_assert(immer::detail::is_dereferenceable_v<Iter>, "" ); |
108 | } |
109 | |
110 | SECTION("pointer" ) |
111 | { |
112 | using Iter = char*; |
113 | static_assert(immer::detail::is_dereferenceable_v<Iter>, "" ); |
114 | } |
115 | |
116 | SECTION("not dereferenceable" ) |
117 | { |
118 | static_assert(not immer::detail::is_dereferenceable_v<int>, "" ); |
119 | } |
120 | } |
121 | |
122 | TEST_CASE("is forward iterator" ) |
123 | { |
124 | SECTION("random access iterator" ) |
125 | { |
126 | using Iter = std::vector<int>::iterator; |
127 | static_assert(immer::detail::is_forward_iterator_v<Iter>, "" ); |
128 | } |
129 | |
130 | SECTION("bidirectional iterator" ) |
131 | { |
132 | using Iter = std::list<int>::iterator; |
133 | static_assert(immer::detail::is_forward_iterator_v<Iter>, "" ); |
134 | } |
135 | |
136 | SECTION("forward iterator" ) |
137 | { |
138 | using Iter = std::forward_list<int>::iterator; |
139 | static_assert(immer::detail::is_forward_iterator_v<Iter>, "" ); |
140 | } |
141 | |
142 | SECTION("input iterator" ) |
143 | { |
144 | using Iter = std::istream_iterator<double>; |
145 | static_assert(not immer::detail::is_forward_iterator_v<Iter>, "" ); |
146 | } |
147 | |
148 | SECTION("output iterator" ) |
149 | { |
150 | using Iter = std::ostream_iterator<double>; |
151 | static_assert(not immer::detail::is_forward_iterator_v<Iter>, "" ); |
152 | } |
153 | |
154 | SECTION("pointer" ) |
155 | { |
156 | using Iter = char*; |
157 | static_assert(immer::detail::is_forward_iterator_v<Iter>, "" ); |
158 | } |
159 | } |
160 | |
161 | TEST_CASE("is iterator" ) |
162 | { |
163 | SECTION("iterator" ) |
164 | { |
165 | using Iter = std::vector<int>::iterator; |
166 | static_assert(immer::detail::is_iterator_v<Iter>, "" ); |
167 | } |
168 | |
169 | SECTION("pointer" ) |
170 | { |
171 | using Iter = char*; |
172 | static_assert(immer::detail::is_iterator_v<Iter>, "" ); |
173 | } |
174 | |
175 | SECTION("not iterator" ) |
176 | { |
177 | static_assert(not immer::detail::is_iterator_v<int>, "" ); |
178 | } |
179 | } |
180 | |
181 | TEST_CASE("provides preincrement" ) |
182 | { |
183 | SECTION("iterator" ) |
184 | { |
185 | using Iter = std::vector<int>::iterator; |
186 | static_assert(immer::detail::is_preincrementable_v<Iter>, "" ); |
187 | } |
188 | |
189 | SECTION("pointer" ) |
190 | { |
191 | using Iter = char*; |
192 | static_assert(immer::detail::is_preincrementable_v<Iter>, "" ); |
193 | } |
194 | |
195 | SECTION("does not provide preincrement" ) |
196 | { |
197 | struct type{}; |
198 | static_assert(not immer::detail::is_preincrementable_v<type>, "" ); |
199 | } |
200 | } |
201 | |
202 | TEST_CASE("void_t" ) |
203 | { |
204 | static_assert(std::is_same<void, immer::detail::void_t<int>>::value, "" ); |
205 | } |
206 | |