Line data Source code
1 : // Pair implementation -*- C++ -*-
2 :
3 : // Copyright (C) 2001-2014 Free Software Foundation, Inc.
4 : //
5 : // This file is part of the GNU ISO C++ Library. This library is free
6 : // software; you can redistribute it and/or modify it under the
7 : // terms of the GNU General Public License as published by the
8 : // Free Software Foundation; either version 3, or (at your option)
9 : // any later version.
10 :
11 : // This library is distributed in the hope that it will be useful,
12 : // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 : // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 : // GNU General Public License for more details.
15 :
16 : // Under Section 7 of GPL version 3, you are granted additional
17 : // permissions described in the GCC Runtime Library Exception, version
18 : // 3.1, as published by the Free Software Foundation.
19 :
20 : // You should have received a copy of the GNU General Public License and
21 : // a copy of the GCC Runtime Library Exception along with this program;
22 : // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
23 : // <http://www.gnu.org/licenses/>.
24 :
25 : /*
26 : *
27 : * Copyright (c) 1994
28 : * Hewlett-Packard Company
29 : *
30 : * Permission to use, copy, modify, distribute and sell this software
31 : * and its documentation for any purpose is hereby granted without fee,
32 : * provided that the above copyright notice appear in all copies and
33 : * that both that copyright notice and this permission notice appear
34 : * in supporting documentation. Hewlett-Packard Company makes no
35 : * representations about the suitability of this software for any
36 : * purpose. It is provided "as is" without express or implied warranty.
37 : *
38 : *
39 : * Copyright (c) 1996,1997
40 : * Silicon Graphics Computer Systems, Inc.
41 : *
42 : * Permission to use, copy, modify, distribute and sell this software
43 : * and its documentation for any purpose is hereby granted without fee,
44 : * provided that the above copyright notice appear in all copies and
45 : * that both that copyright notice and this permission notice appear
46 : * in supporting documentation. Silicon Graphics makes no
47 : * representations about the suitability of this software for any
48 : * purpose. It is provided "as is" without express or implied warranty.
49 : */
50 :
51 : /** @file bits/stl_pair.h
52 : * This is an internal header file, included by other library headers.
53 : * Do not attempt to use it directly. @headername{utility}
54 : */
55 :
56 : #ifndef _STL_PAIR_H
57 : #define _STL_PAIR_H 1
58 :
59 : #include <bits/move.h> // for std::move / std::forward, and std::swap
60 :
61 : #if __cplusplus >= 201103L
62 : #include <type_traits> // for std::__decay_and_strip too
63 : #endif
64 :
65 : namespace std _GLIBCXX_VISIBILITY(default)
66 : {
67 : _GLIBCXX_BEGIN_NAMESPACE_VERSION
68 :
69 : /**
70 : * @addtogroup utilities
71 : * @{
72 : */
73 :
74 : #if __cplusplus >= 201103L
75 : /// piecewise_construct_t
76 : struct piecewise_construct_t { };
77 :
78 : /// piecewise_construct
79 : constexpr piecewise_construct_t piecewise_construct = piecewise_construct_t();
80 :
81 : // Forward declarations.
82 : template<typename...>
83 : class tuple;
84 :
85 : template<std::size_t...>
86 : struct _Index_tuple;
87 : #endif
88 :
89 : /**
90 : * @brief Struct holding two objects of arbitrary type.
91 : *
92 : * @tparam _T1 Type of first object.
93 : * @tparam _T2 Type of second object.
94 : */
95 : template<class _T1, class _T2>
96 11 : struct pair
97 : {
98 : typedef _T1 first_type; /// @c first_type is the first bound type
99 : typedef _T2 second_type; /// @c second_type is the second bound type
100 :
101 : _T1 first; /// @c first is a copy of the first object
102 : _T2 second; /// @c second is a copy of the second object
103 :
104 : // _GLIBCXX_RESOLVE_LIB_DEFECTS
105 : // 265. std::pair::pair() effects overly restrictive
106 : /** The default constructor creates @c first and @c second using their
107 : * respective default constructors. */
108 0 : _GLIBCXX_CONSTEXPR pair()
109 0 : : first(), second() { }
110 :
111 : /** Two objects may be passed to a @c pair constructor to be copied. */
112 0 : _GLIBCXX_CONSTEXPR pair(const _T1& __a, const _T2& __b)
113 0 : : first(__a), second(__b) { }
114 :
115 : /** There is also a templated copy ctor for the @c pair class itself. */
116 : #if __cplusplus < 201103L
117 : template<class _U1, class _U2>
118 : pair(const pair<_U1, _U2>& __p)
119 : : first(__p.first), second(__p.second) { }
120 : #else
121 : template<class _U1, class _U2, class = typename
122 : enable_if<__and_<is_convertible<const _U1&, _T1>,
123 : is_convertible<const _U2&, _T2>>::value>::type>
124 : constexpr pair(const pair<_U1, _U2>& __p)
125 : : first(__p.first), second(__p.second) { }
126 :
127 0 : constexpr pair(const pair&) = default;
128 0 : constexpr pair(pair&&) = default;
129 :
130 : // DR 811.
131 : template<class _U1, class = typename
132 : enable_if<is_convertible<_U1, _T1>::value>::type>
133 0 : constexpr pair(_U1&& __x, const _T2& __y)
134 0 : : first(std::forward<_U1>(__x)), second(__y) { }
135 :
136 : template<class _U2, class = typename
137 : enable_if<is_convertible<_U2, _T2>::value>::type>
138 0 : constexpr pair(const _T1& __x, _U2&& __y)
139 0 : : first(__x), second(std::forward<_U2>(__y)) { }
140 :
141 : template<class _U1, class _U2, class = typename
142 : enable_if<__and_<is_convertible<_U1, _T1>,
143 : is_convertible<_U2, _T2>>::value>::type>
144 11 : constexpr pair(_U1&& __x, _U2&& __y)
145 11 : : first(std::forward<_U1>(__x)), second(std::forward<_U2>(__y)) { }
146 :
147 : template<class _U1, class _U2, class = typename
148 : enable_if<__and_<is_convertible<_U1, _T1>,
149 : is_convertible<_U2, _T2>>::value>::type>
150 : constexpr pair(pair<_U1, _U2>&& __p)
151 : : first(std::forward<_U1>(__p.first)),
152 : second(std::forward<_U2>(__p.second)) { }
153 :
154 : template<typename... _Args1, typename... _Args2>
155 : pair(piecewise_construct_t, tuple<_Args1...>, tuple<_Args2...>);
156 :
157 : pair&
158 : operator=(const pair& __p)
159 : {
160 : first = __p.first;
161 : second = __p.second;
162 : return *this;
163 : }
164 :
165 : pair&
166 0 : operator=(pair&& __p)
167 : noexcept(__and_<is_nothrow_move_assignable<_T1>,
168 : is_nothrow_move_assignable<_T2>>::value)
169 : {
170 0 : first = std::forward<first_type>(__p.first);
171 0 : second = std::forward<second_type>(__p.second);
172 0 : return *this;
173 : }
174 :
175 : template<class _U1, class _U2>
176 : pair&
177 : operator=(const pair<_U1, _U2>& __p)
178 : {
179 : first = __p.first;
180 : second = __p.second;
181 : return *this;
182 : }
183 :
184 : template<class _U1, class _U2>
185 : pair&
186 : operator=(pair<_U1, _U2>&& __p)
187 : {
188 : first = std::forward<_U1>(__p.first);
189 : second = std::forward<_U2>(__p.second);
190 : return *this;
191 : }
192 :
193 : void
194 : swap(pair& __p)
195 : noexcept(noexcept(swap(first, __p.first))
196 : && noexcept(swap(second, __p.second)))
197 : {
198 : using std::swap;
199 : swap(first, __p.first);
200 : swap(second, __p.second);
201 : }
202 :
203 : private:
204 : template<typename... _Args1, std::size_t... _Indexes1,
205 : typename... _Args2, std::size_t... _Indexes2>
206 : pair(tuple<_Args1...>&, tuple<_Args2...>&,
207 : _Index_tuple<_Indexes1...>, _Index_tuple<_Indexes2...>);
208 : #endif
209 : };
210 :
211 : /// Two pairs of the same type are equal iff their members are equal.
212 : template<class _T1, class _T2>
213 : inline _GLIBCXX_CONSTEXPR bool
214 : operator==(const pair<_T1, _T2>& __x, const pair<_T1, _T2>& __y)
215 : { return __x.first == __y.first && __x.second == __y.second; }
216 :
217 : /// <http://gcc.gnu.org/onlinedocs/libstdc++/manual/utilities.html>
218 : template<class _T1, class _T2>
219 : inline _GLIBCXX_CONSTEXPR bool
220 : operator<(const pair<_T1, _T2>& __x, const pair<_T1, _T2>& __y)
221 : { return __x.first < __y.first
222 : || (!(__y.first < __x.first) && __x.second < __y.second); }
223 :
224 : /// Uses @c operator== to find the result.
225 : template<class _T1, class _T2>
226 : inline _GLIBCXX_CONSTEXPR bool
227 : operator!=(const pair<_T1, _T2>& __x, const pair<_T1, _T2>& __y)
228 : { return !(__x == __y); }
229 :
230 : /// Uses @c operator< to find the result.
231 : template<class _T1, class _T2>
232 : inline _GLIBCXX_CONSTEXPR bool
233 : operator>(const pair<_T1, _T2>& __x, const pair<_T1, _T2>& __y)
234 : { return __y < __x; }
235 :
236 : /// Uses @c operator< to find the result.
237 : template<class _T1, class _T2>
238 : inline _GLIBCXX_CONSTEXPR bool
239 : operator<=(const pair<_T1, _T2>& __x, const pair<_T1, _T2>& __y)
240 : { return !(__y < __x); }
241 :
242 : /// Uses @c operator< to find the result.
243 : template<class _T1, class _T2>
244 : inline _GLIBCXX_CONSTEXPR bool
245 : operator>=(const pair<_T1, _T2>& __x, const pair<_T1, _T2>& __y)
246 : { return !(__x < __y); }
247 :
248 : #if __cplusplus >= 201103L
249 : /// See std::pair::swap().
250 : // Note: no std::swap overloads in C++03 mode, this has performance
251 : // implications, see, eg, libstdc++/38466.
252 : template<class _T1, class _T2>
253 : inline void
254 : swap(pair<_T1, _T2>& __x, pair<_T1, _T2>& __y)
255 : noexcept(noexcept(__x.swap(__y)))
256 : { __x.swap(__y); }
257 : #endif
258 :
259 : /**
260 : * @brief A convenience wrapper for creating a pair from two objects.
261 : * @param __x The first object.
262 : * @param __y The second object.
263 : * @return A newly-constructed pair<> object of the appropriate type.
264 : *
265 : * The standard requires that the objects be passed by reference-to-const,
266 : * but LWG issue #181 says they should be passed by const value. We follow
267 : * the LWG by default.
268 : */
269 : // _GLIBCXX_RESOLVE_LIB_DEFECTS
270 : // 181. make_pair() unintended behavior
271 : #if __cplusplus >= 201103L
272 : // NB: DR 706.
273 : template<class _T1, class _T2>
274 : constexpr pair<typename __decay_and_strip<_T1>::__type,
275 : typename __decay_and_strip<_T2>::__type>
276 0 : make_pair(_T1&& __x, _T2&& __y)
277 : {
278 : typedef typename __decay_and_strip<_T1>::__type __ds_type1;
279 : typedef typename __decay_and_strip<_T2>::__type __ds_type2;
280 : typedef pair<__ds_type1, __ds_type2> __pair_type;
281 0 : return __pair_type(std::forward<_T1>(__x), std::forward<_T2>(__y));
282 : }
283 : #else
284 : template<class _T1, class _T2>
285 : inline pair<_T1, _T2>
286 : make_pair(_T1 __x, _T2 __y)
287 : { return pair<_T1, _T2>(__x, __y); }
288 : #endif
289 :
290 : /// @}
291 :
292 : _GLIBCXX_END_NAMESPACE_VERSION
293 : } // namespace std
294 :
295 : #endif /* _STL_PAIR_H */
|