blob: e0ecfdebb8cf30853ff526bce3ae946f418af980 [file] [log] [blame]
Howard Hinnant01afa5c2013-09-02 20:30:37 +00001//===----------------------------------------------------------------------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is dual licensed under the MIT and the University of Illinois Open
6// Source Licenses. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9
10// <optional>
11
12// void swap(optional&)
13// noexcept(is_nothrow_move_constructible<T>::value &&
14// noexcept(swap(declval<T&>(), declval<T&>())));
15
Marshall Clow0cdbe602013-11-15 22:42:10 +000016#include <experimental/optional>
Howard Hinnant01afa5c2013-09-02 20:30:37 +000017#include <type_traits>
18#include <cassert>
19
20#if _LIBCPP_STD_VER > 11
21
Marshall Clow0cdbe602013-11-15 22:42:10 +000022using std::experimental::optional;
23
Howard Hinnant01afa5c2013-09-02 20:30:37 +000024class X
25{
26 int i_;
27public:
28 static unsigned dtor_called;
29 X(int i) : i_(i) {}
30 X(X&& x) = default;
31 X& operator=(X&&) = default;
32 ~X() {++dtor_called;}
33
34 friend bool operator==(const X& x, const X& y) {return x.i_ == y.i_;}
35};
36
37unsigned X::dtor_called = 0;
38
39class Y
40{
41 int i_;
42public:
43 static unsigned dtor_called;
44 Y(int i) : i_(i) {}
45 Y(Y&&) = default;
46 ~Y() {++dtor_called;}
47
48 friend constexpr bool operator==(const Y& x, const Y& y) {return x.i_ == y.i_;}
49 friend void swap(Y& x, Y& y) {std::swap(x.i_, y.i_);}
50};
51
52unsigned Y::dtor_called = 0;
53
54class Z
55{
56 int i_;
57public:
58 Z(int i) : i_(i) {}
59 Z(Z&&) {throw 7;}
60
61 friend constexpr bool operator==(const Z& x, const Z& y) {return x.i_ == y.i_;}
62 friend void swap(Z& x, Z& y) {throw 6;}
63};
64
65
66#endif // _LIBCPP_STD_VER > 11
67
68int main()
69{
70#if _LIBCPP_STD_VER > 11
71 {
Marshall Clow0cdbe602013-11-15 22:42:10 +000072 optional<int> opt1;
73 optional<int> opt2;
Howard Hinnant01afa5c2013-09-02 20:30:37 +000074 static_assert(noexcept(opt1.swap(opt2)) == true, "");
75 assert(static_cast<bool>(opt1) == false);
76 assert(static_cast<bool>(opt2) == false);
77 opt1.swap(opt2);
78 assert(static_cast<bool>(opt1) == false);
79 assert(static_cast<bool>(opt2) == false);
80 }
81 {
Marshall Clow0cdbe602013-11-15 22:42:10 +000082 optional<int> opt1(1);
83 optional<int> opt2;
Howard Hinnant01afa5c2013-09-02 20:30:37 +000084 static_assert(noexcept(opt1.swap(opt2)) == true, "");
85 assert(static_cast<bool>(opt1) == true);
86 assert(*opt1 == 1);
87 assert(static_cast<bool>(opt2) == false);
88 opt1.swap(opt2);
89 assert(static_cast<bool>(opt1) == false);
90 assert(static_cast<bool>(opt2) == true);
91 assert(*opt2 == 1);
92 }
93 {
Marshall Clow0cdbe602013-11-15 22:42:10 +000094 optional<int> opt1;
95 optional<int> opt2(2);
Howard Hinnant01afa5c2013-09-02 20:30:37 +000096 static_assert(noexcept(opt1.swap(opt2)) == true, "");
97 assert(static_cast<bool>(opt1) == false);
98 assert(static_cast<bool>(opt2) == true);
99 assert(*opt2 == 2);
100 opt1.swap(opt2);
101 assert(static_cast<bool>(opt1) == true);
102 assert(*opt1 == 2);
103 assert(static_cast<bool>(opt2) == false);
104 }
105 {
Marshall Clow0cdbe602013-11-15 22:42:10 +0000106 optional<int> opt1(1);
107 optional<int> opt2(2);
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000108 static_assert(noexcept(opt1.swap(opt2)) == true, "");
109 assert(static_cast<bool>(opt1) == true);
110 assert(*opt1 == 1);
111 assert(static_cast<bool>(opt2) == true);
112 assert(*opt2 == 2);
113 opt1.swap(opt2);
114 assert(static_cast<bool>(opt1) == true);
115 assert(*opt1 == 2);
116 assert(static_cast<bool>(opt2) == true);
117 assert(*opt2 == 1);
118 }
119 {
Marshall Clow0cdbe602013-11-15 22:42:10 +0000120 optional<X> opt1;
121 optional<X> opt2;
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000122 static_assert(noexcept(opt1.swap(opt2)) == true, "");
123 assert(static_cast<bool>(opt1) == false);
124 assert(static_cast<bool>(opt2) == false);
125 opt1.swap(opt2);
126 assert(static_cast<bool>(opt1) == false);
127 assert(static_cast<bool>(opt2) == false);
128 assert(X::dtor_called == 0);
129 }
130 {
Marshall Clow0cdbe602013-11-15 22:42:10 +0000131 optional<X> opt1(1);
132 optional<X> opt2;
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000133 static_assert(noexcept(opt1.swap(opt2)) == true, "");
134 assert(static_cast<bool>(opt1) == true);
135 assert(*opt1 == 1);
136 assert(static_cast<bool>(opt2) == false);
137 X::dtor_called = 0;
138 opt1.swap(opt2);
139 assert(X::dtor_called == 1);
140 assert(static_cast<bool>(opt1) == false);
141 assert(static_cast<bool>(opt2) == true);
142 assert(*opt2 == 1);
143 }
144 {
Marshall Clow0cdbe602013-11-15 22:42:10 +0000145 optional<X> opt1;
146 optional<X> opt2(2);
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000147 static_assert(noexcept(opt1.swap(opt2)) == true, "");
148 assert(static_cast<bool>(opt1) == false);
149 assert(static_cast<bool>(opt2) == true);
150 assert(*opt2 == 2);
151 X::dtor_called = 0;
152 opt1.swap(opt2);
153 assert(X::dtor_called == 1);
154 assert(static_cast<bool>(opt1) == true);
155 assert(*opt1 == 2);
156 assert(static_cast<bool>(opt2) == false);
157 }
158 {
Marshall Clow0cdbe602013-11-15 22:42:10 +0000159 optional<X> opt1(1);
160 optional<X> opt2(2);
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000161 static_assert(noexcept(opt1.swap(opt2)) == true, "");
162 assert(static_cast<bool>(opt1) == true);
163 assert(*opt1 == 1);
164 assert(static_cast<bool>(opt2) == true);
165 assert(*opt2 == 2);
166 X::dtor_called = 0;
167 opt1.swap(opt2);
168 assert(X::dtor_called == 1); // from inside std::swap
169 assert(static_cast<bool>(opt1) == true);
170 assert(*opt1 == 2);
171 assert(static_cast<bool>(opt2) == true);
172 assert(*opt2 == 1);
173 }
174 {
Marshall Clow0cdbe602013-11-15 22:42:10 +0000175 optional<Y> opt1;
176 optional<Y> opt2;
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000177 static_assert(noexcept(opt1.swap(opt2)) == false, "");
178 assert(static_cast<bool>(opt1) == false);
179 assert(static_cast<bool>(opt2) == false);
180 opt1.swap(opt2);
181 assert(static_cast<bool>(opt1) == false);
182 assert(static_cast<bool>(opt2) == false);
183 assert(Y::dtor_called == 0);
184 }
185 {
Marshall Clow0cdbe602013-11-15 22:42:10 +0000186 optional<Y> opt1(1);
187 optional<Y> opt2;
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000188 static_assert(noexcept(opt1.swap(opt2)) == false, "");
189 assert(static_cast<bool>(opt1) == true);
190 assert(*opt1 == 1);
191 assert(static_cast<bool>(opt2) == false);
192 Y::dtor_called = 0;
193 opt1.swap(opt2);
194 assert(Y::dtor_called == 1);
195 assert(static_cast<bool>(opt1) == false);
196 assert(static_cast<bool>(opt2) == true);
197 assert(*opt2 == 1);
198 }
199 {
Marshall Clow0cdbe602013-11-15 22:42:10 +0000200 optional<Y> opt1;
201 optional<Y> opt2(2);
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000202 static_assert(noexcept(opt1.swap(opt2)) == false, "");
203 assert(static_cast<bool>(opt1) == false);
204 assert(static_cast<bool>(opt2) == true);
205 assert(*opt2 == 2);
206 Y::dtor_called = 0;
207 opt1.swap(opt2);
208 assert(Y::dtor_called == 1);
209 assert(static_cast<bool>(opt1) == true);
210 assert(*opt1 == 2);
211 assert(static_cast<bool>(opt2) == false);
212 }
213 {
Marshall Clow0cdbe602013-11-15 22:42:10 +0000214 optional<Y> opt1(1);
215 optional<Y> opt2(2);
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000216 static_assert(noexcept(opt1.swap(opt2)) == false, "");
217 assert(static_cast<bool>(opt1) == true);
218 assert(*opt1 == 1);
219 assert(static_cast<bool>(opt2) == true);
220 assert(*opt2 == 2);
221 Y::dtor_called = 0;
222 opt1.swap(opt2);
223 assert(Y::dtor_called == 0);
224 assert(static_cast<bool>(opt1) == true);
225 assert(*opt1 == 2);
226 assert(static_cast<bool>(opt2) == true);
227 assert(*opt2 == 1);
228 }
229 {
Marshall Clow0cdbe602013-11-15 22:42:10 +0000230 optional<Z> opt1;
231 optional<Z> opt2;
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000232 static_assert(noexcept(opt1.swap(opt2)) == false, "");
233 assert(static_cast<bool>(opt1) == false);
234 assert(static_cast<bool>(opt2) == false);
235 opt1.swap(opt2);
236 assert(static_cast<bool>(opt1) == false);
237 assert(static_cast<bool>(opt2) == false);
238 }
239 {
Marshall Clow0cdbe602013-11-15 22:42:10 +0000240 optional<Z> opt1;
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000241 opt1.emplace(1);
Marshall Clow0cdbe602013-11-15 22:42:10 +0000242 optional<Z> opt2;
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000243 static_assert(noexcept(opt1.swap(opt2)) == false, "");
244 assert(static_cast<bool>(opt1) == true);
245 assert(*opt1 == 1);
246 assert(static_cast<bool>(opt2) == false);
247 try
248 {
249 opt1.swap(opt2);
250 assert(false);
251 }
252 catch (int i)
253 {
254 assert(i == 7);
255 }
256 assert(static_cast<bool>(opt1) == true);
257 assert(*opt1 == 1);
258 assert(static_cast<bool>(opt2) == false);
259 }
260 {
Marshall Clow0cdbe602013-11-15 22:42:10 +0000261 optional<Z> opt1;
262 optional<Z> opt2;
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000263 opt2.emplace(2);
264 static_assert(noexcept(opt1.swap(opt2)) == false, "");
265 assert(static_cast<bool>(opt1) == false);
266 assert(static_cast<bool>(opt2) == true);
267 assert(*opt2 == 2);
268 try
269 {
270 opt1.swap(opt2);
271 assert(false);
272 }
273 catch (int i)
274 {
275 assert(i == 7);
276 }
277 assert(static_cast<bool>(opt1) == false);
278 assert(static_cast<bool>(opt2) == true);
279 assert(*opt2 == 2);
280 }
281 {
Marshall Clow0cdbe602013-11-15 22:42:10 +0000282 optional<Z> opt1;
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000283 opt1.emplace(1);
Marshall Clow0cdbe602013-11-15 22:42:10 +0000284 optional<Z> opt2;
Howard Hinnant01afa5c2013-09-02 20:30:37 +0000285 opt2.emplace(2);
286 static_assert(noexcept(opt1.swap(opt2)) == false, "");
287 assert(static_cast<bool>(opt1) == true);
288 assert(*opt1 == 1);
289 assert(static_cast<bool>(opt2) == true);
290 assert(*opt2 == 2);
291 try
292 {
293 opt1.swap(opt2);
294 assert(false);
295 }
296 catch (int i)
297 {
298 assert(i == 6);
299 }
300 assert(static_cast<bool>(opt1) == true);
301 assert(*opt1 == 1);
302 assert(static_cast<bool>(opt2) == true);
303 assert(*opt2 == 2);
304 }
305#endif // _LIBCPP_STD_VER > 11
306}