]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - test/std/containers/unord/unord.map/unord.map.swap/swap_noexcept.pass.cpp
Vendor import of libc++ trunk r300422:
[FreeBSD/FreeBSD.git] / test / std / containers / unord / unord.map / unord.map.swap / swap_noexcept.pass.cpp
1 //===----------------------------------------------------------------------===//
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 // UNSUPPORTED: c++98, c++03
11
12 // <unordered_map>
13
14 // void swap(unordered_map& c)
15 //      noexcept(
16 //          (!allocator_type::propagate_on_container_swap::value ||
17 //           __is_nothrow_swappable<allocator_type>::value) &&
18 //           __is_nothrow_swappable<hasher>::value &&
19 //           __is_nothrow_swappable<key_equal>::value);
20 //
21 //  In C++17, the standard says that swap shall have:
22 //     noexcept(allocator_traits<Allocator>::is_always_equal::value &&
23 //               noexcept(swap(declval<Hash&>(), declval<Hash&>())) &&
24 //               noexcept(swap(declval<Pred&>(), declval<Pred&>())));
25
26 // This tests a conforming extension
27
28 #include <unordered_map>
29 #include <utility>
30 #include <cassert>
31
32 #include "test_macros.h"
33 #include "MoveOnly.h"
34 #include "test_allocator.h"
35
36 template <class T>
37 struct some_comp
38 {
39     typedef T value_type;
40
41     some_comp() {}
42     some_comp(const some_comp&) {}
43     bool operator()(const T&, const T&) const { return false; }
44 };
45
46 template <class T>
47 struct some_comp2
48 {
49     typedef T value_type;
50
51     some_comp2() {}
52     some_comp2(const some_comp2&) {}
53     bool operator()(const T&, const T&) const { return false; }
54 };
55
56 #if TEST_STD_VER >= 14
57 template <typename T>
58 void swap(some_comp2<T>&, some_comp2<T>&) noexcept {}
59 #endif
60
61 template <class T>
62 struct some_hash
63 {
64     typedef T value_type;
65     some_hash() {}
66     some_hash(const some_hash&);
67     std::size_t operator()(T const&) const;
68 };
69
70 template <class T>
71 struct some_hash2
72 {
73     typedef T value_type;
74     some_hash2() {}
75     some_hash2(const some_hash2&);
76     std::size_t operator()(T const&) const;
77 };
78
79 #if TEST_STD_VER >= 14
80 template <typename T>
81 void swap(some_hash2<T>&, some_hash2<T>&) noexcept {}
82 #endif
83
84 template <class T>
85 struct some_alloc
86 {
87     typedef T value_type;
88
89     some_alloc() {}
90     some_alloc(const some_alloc&);
91     void deallocate(void*, unsigned) {}
92
93     typedef std::true_type propagate_on_container_swap;
94 };
95
96 template <class T>
97 struct some_alloc2
98 {
99     typedef T value_type;
100
101     some_alloc2() {}
102     some_alloc2(const some_alloc2&);
103     void deallocate(void*, unsigned) {}
104
105     typedef std::false_type propagate_on_container_swap;
106     typedef std::true_type is_always_equal;
107 };
108
109 template <class T>
110 struct some_alloc3
111 {
112     typedef T value_type;
113
114     some_alloc3() {}
115     some_alloc3(const some_alloc3&);
116     void deallocate(void*, unsigned) {}
117
118     typedef std::false_type propagate_on_container_swap;
119     typedef std::false_type is_always_equal;
120 };
121
122
123 int main()
124 {
125         typedef std::pair<const MoveOnly, MoveOnly> MapType;
126     {
127         typedef std::unordered_map<MoveOnly, MoveOnly> C;
128         static_assert(noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
129     }
130 #if defined(_LIBCPP_VERSION)
131     {
132         typedef std::unordered_map<MoveOnly, MoveOnly, std::hash<MoveOnly>,
133                            std::equal_to<MoveOnly>, test_allocator<MapType>> C;
134         static_assert(noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
135     }
136     {
137         typedef std::unordered_map<MoveOnly, MoveOnly, std::hash<MoveOnly>,
138                           std::equal_to<MoveOnly>, other_allocator<MapType>> C;
139         static_assert(noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
140     }
141 #endif // _LIBCPP_VERSION
142     {
143         typedef std::unordered_map<MoveOnly, MoveOnly, some_hash<MoveOnly>> C;
144         static_assert(!noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
145     }
146     {
147         typedef std::unordered_map<MoveOnly, MoveOnly, std::hash<MoveOnly>,
148                                                          some_comp<MoveOnly>> C;
149         static_assert(!noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
150     }
151
152 #if TEST_STD_VER >= 14
153     { // POCS allocator, throwable swap for hash, throwable swap for comp
154     typedef std::unordered_map<MoveOnly, MoveOnly, some_hash<MoveOnly>, some_comp <MoveOnly>, some_alloc <MapType>> C;
155     static_assert(!noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
156     }
157     { // always equal allocator, throwable swap for hash, throwable swap for comp
158     typedef std::unordered_map<MoveOnly, MoveOnly, some_hash<MoveOnly>, some_comp <MoveOnly>, some_alloc2<MapType>> C;
159     static_assert(!noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
160     }
161     { // POCS allocator, throwable swap for hash, nothrow swap for comp
162     typedef std::unordered_map<MoveOnly, MoveOnly, some_hash<MoveOnly>, some_comp2<MoveOnly>, some_alloc <MapType>> C;
163     static_assert(!noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
164     }
165     { // always equal allocator, throwable swap for hash, nothrow swap for comp
166     typedef std::unordered_map<MoveOnly, MoveOnly, some_hash<MoveOnly>, some_comp2<MoveOnly>, some_alloc2<MapType>> C;
167     static_assert(!noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
168     }
169     { // POCS allocator, nothrow swap for hash, throwable swap for comp
170     typedef std::unordered_map<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp <MoveOnly>, some_alloc <MapType>> C;
171     static_assert(!noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
172     }
173     { // always equal allocator, nothrow swap for hash, throwable swap for comp
174     typedef std::unordered_map<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp <MoveOnly>, some_alloc2<MapType>> C;
175     static_assert(!noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
176     }
177     { // POCS allocator, nothrow swap for hash, nothrow swap for comp
178     typedef std::unordered_map<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc <MapType>> C;
179     static_assert( noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
180     }
181     { // always equal allocator, nothrow swap for hash, nothrow swap for comp
182     typedef std::unordered_map<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc2<MapType>> C;
183     static_assert( noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
184     }
185 #if defined(_LIBCPP_VERSION)
186     { // NOT always equal allocator, nothrow swap for hash, nothrow swap for comp
187     typedef std::unordered_map<MoveOnly, MoveOnly, some_hash2<MoveOnly>, some_comp2<MoveOnly>, some_alloc3<MapType>> C;
188     static_assert( noexcept(swap(std::declval<C&>(), std::declval<C&>())), "");
189     }
190 #endif // _LIBCPP_VERSION
191 #endif
192 }