1f2f7d72fSLouis Dionne //===----------------------------------------------------------------------===//
2f2f7d72fSLouis Dionne //
3f2f7d72fSLouis Dionne // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4f2f7d72fSLouis Dionne // See https://llvm.org/LICENSE.txt for license information.
5f2f7d72fSLouis Dionne // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6f2f7d72fSLouis Dionne //
7f2f7d72fSLouis Dionne //===----------------------------------------------------------------------===//
8f2f7d72fSLouis Dionne
9f2f7d72fSLouis Dionne // <map>
1031cbe0f2SLouis Dionne // UNSUPPORTED: c++03, c++11, c++14
11f2f7d72fSLouis Dionne
12f2f7d72fSLouis Dionne // template<class InputIterator,
13f2f7d72fSLouis Dionne // class Compare = less<iter-value-type<InputIterator>>,
14f2f7d72fSLouis Dionne // class Allocator = allocator<iter-value-type<InputIterator>>>
15f2f7d72fSLouis Dionne // map(InputIterator, InputIterator,
16f2f7d72fSLouis Dionne // Compare = Compare(), Allocator = Allocator())
17f2f7d72fSLouis Dionne // -> map<iter-value-type<InputIterator>, Compare, Allocator>;
18f2f7d72fSLouis Dionne // template<class Key, class Compare = less<Key>, class Allocator = allocator<Key>>
19f2f7d72fSLouis Dionne // map(initializer_list<Key>, Compare = Compare(), Allocator = Allocator())
20f2f7d72fSLouis Dionne // -> map<Key, Compare, Allocator>;
21f2f7d72fSLouis Dionne // template<class InputIterator, class Allocator>
22f2f7d72fSLouis Dionne // map(InputIterator, InputIterator, Allocator)
23f2f7d72fSLouis Dionne // -> map<iter-value-type<InputIterator>, less<iter-value-type<InputIterator>>, Allocator>;
24f2f7d72fSLouis Dionne // template<class Key, class Allocator>
25f2f7d72fSLouis Dionne // map(initializer_list<Key>, Allocator)
26f2f7d72fSLouis Dionne // -> map<Key, less<Key>, Allocator>;
27*ef70fe4dSvarconst //
28*ef70fe4dSvarconst // template<ranges::input_range R, class Compare = less<range-key-type<R>,
29*ef70fe4dSvarconst // class Allocator = allocator<range-to-alloc-type<R>>>
30*ef70fe4dSvarconst // map(from_range_t, R&&, Compare = Compare(), Allocator = Allocator())
31*ef70fe4dSvarconst // -> map<range-key-type<R>, range-mapped-type<R>, Compare, Allocator>; // C++23
32*ef70fe4dSvarconst //
33*ef70fe4dSvarconst // template<ranges::input_range R, class Allocator>
34*ef70fe4dSvarconst // map(from_range_t, R&&, Allocator)
35*ef70fe4dSvarconst // -> map<range-key-type<R>, range-mapped-type<R>, less<range-key-type<R>>, Allocator>; // C++23
36f2f7d72fSLouis Dionne
37f2f7d72fSLouis Dionne #include <algorithm> // std::equal
38*ef70fe4dSvarconst #include <array>
39f2f7d72fSLouis Dionne #include <cassert>
40f2f7d72fSLouis Dionne #include <climits> // INT_MAX
41f2f7d72fSLouis Dionne #include <functional>
42f2f7d72fSLouis Dionne #include <map>
43f2f7d72fSLouis Dionne #include <type_traits>
44f2f7d72fSLouis Dionne
4568072a71SKonstantin Varlamov #include "deduction_guides_sfinae_checks.h"
46f2f7d72fSLouis Dionne #include "test_allocator.h"
47f2f7d72fSLouis Dionne
48f2f7d72fSLouis Dionne using P = std::pair<int, long>;
49f2f7d72fSLouis Dionne using PC = std::pair<const int, long>;
50f2f7d72fSLouis Dionne
main(int,char **)51f2f7d72fSLouis Dionne int main(int, char**)
52f2f7d72fSLouis Dionne {
53f2f7d72fSLouis Dionne {
54f2f7d72fSLouis Dionne const P arr[] = { {1,1L}, {2,2L}, {1,1L}, {INT_MAX,1L}, {3,1L} };
55f2f7d72fSLouis Dionne std::map m(std::begin(arr), std::end(arr));
56f2f7d72fSLouis Dionne
57f2f7d72fSLouis Dionne ASSERT_SAME_TYPE(decltype(m), std::map<int, long>);
58f2f7d72fSLouis Dionne const PC expected_m[] = { {1,1L}, {2,2L}, {3,1L}, {INT_MAX,1L} };
59f2f7d72fSLouis Dionne assert(std::equal(m.begin(), m.end(), std::begin(expected_m), std::end(expected_m)));
60f2f7d72fSLouis Dionne }
61f2f7d72fSLouis Dionne
62f2f7d72fSLouis Dionne {
63f2f7d72fSLouis Dionne const P arr[] = { {1,1L}, {2,2L}, {1,1L}, {INT_MAX,1L}, {3,1L} };
64f2f7d72fSLouis Dionne std::map m(std::begin(arr), std::end(arr), std::greater<int>());
65f2f7d72fSLouis Dionne
66f2f7d72fSLouis Dionne ASSERT_SAME_TYPE(decltype(m), std::map<int, long, std::greater<int>>);
67f2f7d72fSLouis Dionne const PC expected_m[] = { {INT_MAX,1L}, {3,1L}, {2,2L}, {1,1L} };
68f2f7d72fSLouis Dionne assert(std::equal(m.begin(), m.end(), std::begin(expected_m), std::end(expected_m)));
69f2f7d72fSLouis Dionne }
70f2f7d72fSLouis Dionne
71f2f7d72fSLouis Dionne {
72f2f7d72fSLouis Dionne const P arr[] = { {1,1L}, {2,2L}, {1,1L}, {INT_MAX,1L}, {3,1L} };
73f2f7d72fSLouis Dionne std::map m(std::begin(arr), std::end(arr), std::greater<int>(), test_allocator<PC>(0, 42));
74f2f7d72fSLouis Dionne
75f2f7d72fSLouis Dionne ASSERT_SAME_TYPE(decltype(m), std::map<int, long, std::greater<int>, test_allocator<PC>>);
76f2f7d72fSLouis Dionne const PC expected_m[] = { {INT_MAX,1L}, {3,1L}, {2,2L}, {1,1L} };
77f2f7d72fSLouis Dionne assert(std::equal(m.begin(), m.end(), std::begin(expected_m), std::end(expected_m)));
78f2f7d72fSLouis Dionne assert(m.get_allocator().get_id() == 42);
79f2f7d72fSLouis Dionne }
80f2f7d72fSLouis Dionne
81f2f7d72fSLouis Dionne {
82f2f7d72fSLouis Dionne std::map<int, long> source;
83f2f7d72fSLouis Dionne std::map m(source);
84f2f7d72fSLouis Dionne ASSERT_SAME_TYPE(decltype(m), decltype(source));
85f2f7d72fSLouis Dionne assert(m.size() == 0);
86f2f7d72fSLouis Dionne }
87f2f7d72fSLouis Dionne
88f2f7d72fSLouis Dionne {
89f2f7d72fSLouis Dionne std::map<int, long> source;
90f2f7d72fSLouis Dionne std::map m{source}; // braces instead of parens
91f2f7d72fSLouis Dionne ASSERT_SAME_TYPE(decltype(m), decltype(source));
92f2f7d72fSLouis Dionne assert(m.size() == 0);
93f2f7d72fSLouis Dionne }
94f2f7d72fSLouis Dionne
95f2f7d72fSLouis Dionne {
96f2f7d72fSLouis Dionne std::map<int, long> source;
97f2f7d72fSLouis Dionne std::map m(source, std::map<int, long>::allocator_type());
98f2f7d72fSLouis Dionne ASSERT_SAME_TYPE(decltype(m), decltype(source));
99f2f7d72fSLouis Dionne assert(m.size() == 0);
100f2f7d72fSLouis Dionne }
101f2f7d72fSLouis Dionne
102f2f7d72fSLouis Dionne {
103f2f7d72fSLouis Dionne std::map m{ P{1,1L}, P{2,2L}, P{1,1L}, P{INT_MAX,1L}, P{3,1L} };
104f2f7d72fSLouis Dionne
105f2f7d72fSLouis Dionne ASSERT_SAME_TYPE(decltype(m), std::map<int, long>);
106f2f7d72fSLouis Dionne const PC expected_m[] = { {1,1L}, {2,2L}, {3,1L}, {INT_MAX,1L} };
107f2f7d72fSLouis Dionne assert(std::equal(m.begin(), m.end(), std::begin(expected_m), std::end(expected_m)));
108f2f7d72fSLouis Dionne }
109f2f7d72fSLouis Dionne
110f2f7d72fSLouis Dionne {
111f2f7d72fSLouis Dionne std::map m({ P{1,1L}, P{2,2L}, P{1,1L}, P{INT_MAX,1L}, P{3,1L} }, std::greater<int>());
112f2f7d72fSLouis Dionne
113f2f7d72fSLouis Dionne ASSERT_SAME_TYPE(decltype(m), std::map<int, long, std::greater<int>>);
114f2f7d72fSLouis Dionne const PC expected_m[] = { {INT_MAX,1L}, {3,1L}, {2,2L}, {1,1L} };
115f2f7d72fSLouis Dionne assert(std::equal(m.begin(), m.end(), std::begin(expected_m), std::end(expected_m)));
116f2f7d72fSLouis Dionne }
117f2f7d72fSLouis Dionne
118f2f7d72fSLouis Dionne {
119f2f7d72fSLouis Dionne std::map m({ P{1,1L}, P{2,2L}, P{1,1L}, P{INT_MAX,1L}, P{3,1L} }, std::greater<int>(), test_allocator<PC>(0, 43));
120f2f7d72fSLouis Dionne
121f2f7d72fSLouis Dionne ASSERT_SAME_TYPE(decltype(m), std::map<int, long, std::greater<int>, test_allocator<PC>>);
122f2f7d72fSLouis Dionne const PC expected_m[] = { {INT_MAX,1L}, {3,1L}, {2,2L}, {1,1L} };
123f2f7d72fSLouis Dionne assert(std::equal(m.begin(), m.end(), std::begin(expected_m), std::end(expected_m)));
124f2f7d72fSLouis Dionne assert(m.get_allocator().get_id() == 43);
125f2f7d72fSLouis Dionne }
126f2f7d72fSLouis Dionne
127f2f7d72fSLouis Dionne {
128f2f7d72fSLouis Dionne const P arr[] = { {1,1L}, {2,2L}, {1,1L}, {INT_MAX,1L}, {3,1L} };
129f2f7d72fSLouis Dionne std::map m(std::begin(arr), std::end(arr), test_allocator<PC>(0, 44));
130f2f7d72fSLouis Dionne
131f2f7d72fSLouis Dionne ASSERT_SAME_TYPE(decltype(m), std::map<int, long, std::less<int>, test_allocator<PC>>);
132f2f7d72fSLouis Dionne const PC expected_m[] = { {1,1L}, {2,2L}, {3,1L}, {INT_MAX,1L} };
133f2f7d72fSLouis Dionne assert(std::equal(m.begin(), m.end(), std::begin(expected_m), std::end(expected_m)));
134f2f7d72fSLouis Dionne assert(m.get_allocator().get_id() == 44);
135f2f7d72fSLouis Dionne }
136f2f7d72fSLouis Dionne
137f2f7d72fSLouis Dionne {
138f2f7d72fSLouis Dionne std::map m({ P{1,1L}, P{2,2L}, P{1,1L}, P{INT_MAX,1L}, P{3,1L} }, test_allocator<PC>(0, 45));
139f2f7d72fSLouis Dionne
140f2f7d72fSLouis Dionne ASSERT_SAME_TYPE(decltype(m), std::map<int, long, std::less<int>, test_allocator<PC>>);
141f2f7d72fSLouis Dionne const PC expected_m[] = { {1,1L}, {2,2L}, {3,1L}, {INT_MAX,1L} };
142f2f7d72fSLouis Dionne assert(std::equal(m.begin(), m.end(), std::begin(expected_m), std::end(expected_m)));
143f2f7d72fSLouis Dionne assert(m.get_allocator().get_id() == 45);
144f2f7d72fSLouis Dionne }
145f2f7d72fSLouis Dionne
146dd15c272SArthur O'Dwyer {
147dd15c272SArthur O'Dwyer // Examples from LWG3025
148dd15c272SArthur O'Dwyer std::map m{std::pair{1, 1}, {2, 2}, {3, 3}};
149dd15c272SArthur O'Dwyer ASSERT_SAME_TYPE(decltype(m), std::map<int, int>);
150dd15c272SArthur O'Dwyer
151dd15c272SArthur O'Dwyer std::map m2{m.begin(), m.end()};
152dd15c272SArthur O'Dwyer ASSERT_SAME_TYPE(decltype(m2), std::map<int, int>);
153dd15c272SArthur O'Dwyer }
154dd15c272SArthur O'Dwyer
155dd15c272SArthur O'Dwyer {
156dd15c272SArthur O'Dwyer // Examples from LWG3531
157dd15c272SArthur O'Dwyer std::map m1{{std::pair{1, 2}, {3, 4}}, std::less<int>()};
158dd15c272SArthur O'Dwyer ASSERT_SAME_TYPE(decltype(m1), std::map<int, int>);
159dd15c272SArthur O'Dwyer
160dd15c272SArthur O'Dwyer using value_type = std::pair<const int, int>;
161dd15c272SArthur O'Dwyer std::map m2{{value_type{1, 2}, {3, 4}}, std::less<int>()};
162dd15c272SArthur O'Dwyer ASSERT_SAME_TYPE(decltype(m2), std::map<int, int>);
163dd15c272SArthur O'Dwyer }
164dd15c272SArthur O'Dwyer
165*ef70fe4dSvarconst #if TEST_STD_VER >= 23
166*ef70fe4dSvarconst {
167*ef70fe4dSvarconst using Range = std::array<P, 0>;
168*ef70fe4dSvarconst using Comp = std::greater<int>;
169*ef70fe4dSvarconst using DefaultComp = std::less<int>;
170*ef70fe4dSvarconst using Alloc = test_allocator<PC>;
171*ef70fe4dSvarconst
172*ef70fe4dSvarconst { // (from_range, range)
173*ef70fe4dSvarconst std::map c(std::from_range, Range());
174*ef70fe4dSvarconst static_assert(std::is_same_v<decltype(c), std::map<int, long>>);
175*ef70fe4dSvarconst }
176*ef70fe4dSvarconst
177*ef70fe4dSvarconst { // (from_range, range, comp)
178*ef70fe4dSvarconst std::map c(std::from_range, Range(), Comp());
179*ef70fe4dSvarconst static_assert(std::is_same_v<decltype(c), std::map<int, long, Comp>>);
180*ef70fe4dSvarconst }
181*ef70fe4dSvarconst
182*ef70fe4dSvarconst { // (from_range, range, comp, alloc)
183*ef70fe4dSvarconst std::map c(std::from_range, Range(), Comp(), Alloc());
184*ef70fe4dSvarconst static_assert(std::is_same_v<decltype(c), std::map<int, long, Comp, Alloc>>);
185*ef70fe4dSvarconst }
186*ef70fe4dSvarconst
187*ef70fe4dSvarconst { // (from_range, range, alloc)
188*ef70fe4dSvarconst std::map c(std::from_range, Range(), Alloc());
189*ef70fe4dSvarconst static_assert(std::is_same_v<decltype(c), std::map<int, long, DefaultComp, Alloc>>);
190*ef70fe4dSvarconst }
191*ef70fe4dSvarconst }
192*ef70fe4dSvarconst #endif
193*ef70fe4dSvarconst
19468072a71SKonstantin Varlamov AssociativeContainerDeductionGuidesSfinaeAway<std::map, std::map<int, long>>();
19568072a71SKonstantin Varlamov
196f2f7d72fSLouis Dionne return 0;
197f2f7d72fSLouis Dionne }
198