1*38fd1498Szrj // Profiling multiset implementation -*- C++ -*-
2*38fd1498Szrj
3*38fd1498Szrj // Copyright (C) 2009-2018 Free Software Foundation, Inc.
4*38fd1498Szrj //
5*38fd1498Szrj // This file is part of the GNU ISO C++ Library. This library is free
6*38fd1498Szrj // software; you can redistribute it and/or modify it under the
7*38fd1498Szrj // terms of the GNU General Public License as published by the
8*38fd1498Szrj // Free Software Foundation; either version 3, or (at your option)
9*38fd1498Szrj // any later version.
10*38fd1498Szrj
11*38fd1498Szrj // This library is distributed in the hope that it will be useful,
12*38fd1498Szrj // but WITHOUT ANY WARRANTY; without even the implied warranty of
13*38fd1498Szrj // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14*38fd1498Szrj // GNU General Public License for more details.
15*38fd1498Szrj
16*38fd1498Szrj // Under Section 7 of GPL version 3, you are granted additional
17*38fd1498Szrj // permissions described in the GCC Runtime Library Exception, version
18*38fd1498Szrj // 3.1, as published by the Free Software Foundation.
19*38fd1498Szrj
20*38fd1498Szrj // You should have received a copy of the GNU General Public License and
21*38fd1498Szrj // a copy of the GCC Runtime Library Exception along with this program;
22*38fd1498Szrj // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
23*38fd1498Szrj // <http://www.gnu.org/licenses/>.
24*38fd1498Szrj
25*38fd1498Szrj /** @file profile/multiset.h
26*38fd1498Szrj * This file is a GNU profile extension to the Standard C++ Library.
27*38fd1498Szrj */
28*38fd1498Szrj
29*38fd1498Szrj #ifndef _GLIBCXX_PROFILE_MULTISET_H
30*38fd1498Szrj #define _GLIBCXX_PROFILE_MULTISET_H 1
31*38fd1498Szrj
32*38fd1498Szrj #include <profile/base.h>
33*38fd1498Szrj #include <profile/ordered_base.h>
34*38fd1498Szrj
_GLIBCXX_VISIBILITY(default)35*38fd1498Szrj namespace std _GLIBCXX_VISIBILITY(default)
36*38fd1498Szrj {
37*38fd1498Szrj namespace __profile
38*38fd1498Szrj {
39*38fd1498Szrj /// Class std::multiset wrapper with performance instrumentation.
40*38fd1498Szrj template<typename _Key, typename _Compare = std::less<_Key>,
41*38fd1498Szrj typename _Allocator = std::allocator<_Key> >
42*38fd1498Szrj class multiset
43*38fd1498Szrj : public _GLIBCXX_STD_C::multiset<_Key, _Compare, _Allocator>,
44*38fd1498Szrj public _Ordered_profile<multiset<_Key, _Compare, _Allocator> >
45*38fd1498Szrj {
46*38fd1498Szrj typedef _GLIBCXX_STD_C::multiset<_Key, _Compare, _Allocator> _Base;
47*38fd1498Szrj
48*38fd1498Szrj typedef typename _Base::iterator _Base_iterator;
49*38fd1498Szrj typedef typename _Base::const_iterator _Base_const_iterator;
50*38fd1498Szrj
51*38fd1498Szrj public:
52*38fd1498Szrj // types:
53*38fd1498Szrj typedef _Key key_type;
54*38fd1498Szrj typedef _Key value_type;
55*38fd1498Szrj typedef _Compare key_compare;
56*38fd1498Szrj typedef _Compare value_compare;
57*38fd1498Szrj typedef _Allocator allocator_type;
58*38fd1498Szrj typedef typename _Base::reference reference;
59*38fd1498Szrj typedef typename _Base::const_reference const_reference;
60*38fd1498Szrj
61*38fd1498Szrj typedef __iterator_tracker<_Base_iterator,
62*38fd1498Szrj multiset> iterator;
63*38fd1498Szrj typedef __iterator_tracker<_Base_const_iterator,
64*38fd1498Szrj multiset> const_iterator;
65*38fd1498Szrj typedef std::reverse_iterator<iterator> reverse_iterator;
66*38fd1498Szrj typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
67*38fd1498Szrj
68*38fd1498Szrj typedef typename _Base::size_type size_type;
69*38fd1498Szrj typedef typename _Base::difference_type difference_type;
70*38fd1498Szrj
71*38fd1498Szrj // 23.3.3.1 construct/copy/destroy:
72*38fd1498Szrj
73*38fd1498Szrj #if __cplusplus < 201103L
74*38fd1498Szrj multiset()
75*38fd1498Szrj : _Base() { }
76*38fd1498Szrj multiset(const multiset& __x)
77*38fd1498Szrj : _Base(__x) { }
78*38fd1498Szrj ~multiset() { }
79*38fd1498Szrj #else
80*38fd1498Szrj multiset() = default;
81*38fd1498Szrj multiset(const multiset&) = default;
82*38fd1498Szrj multiset(multiset&&) = default;
83*38fd1498Szrj ~multiset() = default;
84*38fd1498Szrj #endif
85*38fd1498Szrj
86*38fd1498Szrj explicit multiset(const _Compare& __comp,
87*38fd1498Szrj const _Allocator& __a = _Allocator())
88*38fd1498Szrj : _Base(__comp, __a) { }
89*38fd1498Szrj
90*38fd1498Szrj #if __cplusplus >= 201103L
91*38fd1498Szrj template<typename _InputIterator,
92*38fd1498Szrj typename = std::_RequireInputIter<_InputIterator>>
93*38fd1498Szrj #else
94*38fd1498Szrj template<typename _InputIterator>
95*38fd1498Szrj #endif
96*38fd1498Szrj multiset(_InputIterator __first, _InputIterator __last,
97*38fd1498Szrj const _Compare& __comp = _Compare(),
98*38fd1498Szrj const _Allocator& __a = _Allocator())
99*38fd1498Szrj : _Base(__first, __last, __comp, __a) { }
100*38fd1498Szrj
101*38fd1498Szrj #if __cplusplus >= 201103L
102*38fd1498Szrj multiset(initializer_list<value_type> __l,
103*38fd1498Szrj const _Compare& __comp = _Compare(),
104*38fd1498Szrj const allocator_type& __a = allocator_type())
105*38fd1498Szrj : _Base(__l, __comp, __a) { }
106*38fd1498Szrj
107*38fd1498Szrj explicit
108*38fd1498Szrj multiset(const allocator_type& __a)
109*38fd1498Szrj : _Base(__a) { }
110*38fd1498Szrj
111*38fd1498Szrj multiset(const multiset& __x, const allocator_type& __a)
112*38fd1498Szrj : _Base(__x, __a) { }
113*38fd1498Szrj
114*38fd1498Szrj multiset(multiset&& __x, const allocator_type& __a)
115*38fd1498Szrj noexcept( noexcept(_Base(std::move(__x), __a)) )
116*38fd1498Szrj : _Base(std::move(__x), __a) { }
117*38fd1498Szrj
118*38fd1498Szrj multiset(initializer_list<value_type> __l, const allocator_type& __a)
119*38fd1498Szrj : _Base(__l, __a) { }
120*38fd1498Szrj
121*38fd1498Szrj template<typename _InputIterator>
122*38fd1498Szrj multiset(_InputIterator __first, _InputIterator __last,
123*38fd1498Szrj const allocator_type& __a)
124*38fd1498Szrj : _Base(__first, __last, __a) { }
125*38fd1498Szrj #endif
126*38fd1498Szrj
127*38fd1498Szrj multiset(const _Base& __x)
128*38fd1498Szrj : _Base(__x) { }
129*38fd1498Szrj
130*38fd1498Szrj #if __cplusplus < 201103L
131*38fd1498Szrj multiset&
132*38fd1498Szrj operator=(const multiset& __x)
133*38fd1498Szrj {
134*38fd1498Szrj this->_M_profile_destruct();
135*38fd1498Szrj _M_base() = __x;
136*38fd1498Szrj this->_M_profile_construct();
137*38fd1498Szrj return *this;
138*38fd1498Szrj }
139*38fd1498Szrj #else
140*38fd1498Szrj multiset&
141*38fd1498Szrj operator=(const multiset&) = default;
142*38fd1498Szrj
143*38fd1498Szrj multiset&
144*38fd1498Szrj operator=(multiset&&) = default;
145*38fd1498Szrj
146*38fd1498Szrj multiset&
147*38fd1498Szrj operator=(initializer_list<value_type> __l)
148*38fd1498Szrj {
149*38fd1498Szrj this->_M_profile_destruct();
150*38fd1498Szrj _M_base() = __l;
151*38fd1498Szrj this->_M_profile_construct();
152*38fd1498Szrj return *this;
153*38fd1498Szrj }
154*38fd1498Szrj #endif
155*38fd1498Szrj
156*38fd1498Szrj // iterators
157*38fd1498Szrj iterator
158*38fd1498Szrj begin() _GLIBCXX_NOEXCEPT
159*38fd1498Szrj { return iterator(_Base::begin(), this); }
160*38fd1498Szrj
161*38fd1498Szrj const_iterator
162*38fd1498Szrj begin() const _GLIBCXX_NOEXCEPT
163*38fd1498Szrj { return const_iterator(_Base::begin(), this); }
164*38fd1498Szrj
165*38fd1498Szrj iterator
166*38fd1498Szrj end() _GLIBCXX_NOEXCEPT
167*38fd1498Szrj { return iterator(_Base::end(), this); }
168*38fd1498Szrj
169*38fd1498Szrj const_iterator
170*38fd1498Szrj end() const _GLIBCXX_NOEXCEPT
171*38fd1498Szrj { return const_iterator(_Base::end(), this); }
172*38fd1498Szrj
173*38fd1498Szrj #if __cplusplus >= 201103L
174*38fd1498Szrj const_iterator
175*38fd1498Szrj cbegin() const noexcept
176*38fd1498Szrj { return const_iterator(_Base::cbegin(), this); }
177*38fd1498Szrj
178*38fd1498Szrj const_iterator
179*38fd1498Szrj cend() const noexcept
180*38fd1498Szrj { return const_iterator(_Base::cend(), this); }
181*38fd1498Szrj #endif
182*38fd1498Szrj
183*38fd1498Szrj reverse_iterator
184*38fd1498Szrj rbegin() _GLIBCXX_NOEXCEPT
185*38fd1498Szrj {
186*38fd1498Szrj __profcxx_map2umap_invalidate(this->_M_map2umap_info);
187*38fd1498Szrj return reverse_iterator(end());
188*38fd1498Szrj }
189*38fd1498Szrj
190*38fd1498Szrj const_reverse_iterator
191*38fd1498Szrj rbegin() const _GLIBCXX_NOEXCEPT
192*38fd1498Szrj {
193*38fd1498Szrj __profcxx_map2umap_invalidate(this->_M_map2umap_info);
194*38fd1498Szrj return const_reverse_iterator(end());
195*38fd1498Szrj }
196*38fd1498Szrj
197*38fd1498Szrj reverse_iterator
198*38fd1498Szrj rend() _GLIBCXX_NOEXCEPT
199*38fd1498Szrj {
200*38fd1498Szrj __profcxx_map2umap_invalidate(this->_M_map2umap_info);
201*38fd1498Szrj return reverse_iterator(begin());
202*38fd1498Szrj }
203*38fd1498Szrj
204*38fd1498Szrj const_reverse_iterator
205*38fd1498Szrj rend() const _GLIBCXX_NOEXCEPT
206*38fd1498Szrj {
207*38fd1498Szrj __profcxx_map2umap_invalidate(this->_M_map2umap_info);
208*38fd1498Szrj return const_reverse_iterator(begin());
209*38fd1498Szrj }
210*38fd1498Szrj
211*38fd1498Szrj #if __cplusplus >= 201103L
212*38fd1498Szrj const_reverse_iterator
213*38fd1498Szrj crbegin() const noexcept
214*38fd1498Szrj {
215*38fd1498Szrj __profcxx_map2umap_invalidate(this->_M_map2umap_info);
216*38fd1498Szrj return const_reverse_iterator(cend());
217*38fd1498Szrj }
218*38fd1498Szrj
219*38fd1498Szrj const_reverse_iterator
220*38fd1498Szrj crend() const noexcept
221*38fd1498Szrj {
222*38fd1498Szrj __profcxx_map2umap_invalidate(this->_M_map2umap_info);
223*38fd1498Szrj return const_reverse_iterator(cbegin());
224*38fd1498Szrj }
225*38fd1498Szrj #endif
226*38fd1498Szrj
227*38fd1498Szrj void
228*38fd1498Szrj swap(multiset& __x)
229*38fd1498Szrj _GLIBCXX_NOEXCEPT_IF( noexcept(declval<_Base&>().swap(__x)) )
230*38fd1498Szrj {
231*38fd1498Szrj _Base::swap(__x);
232*38fd1498Szrj this->_M_swap(__x);
233*38fd1498Szrj }
234*38fd1498Szrj
235*38fd1498Szrj // modifiers:
236*38fd1498Szrj #if __cplusplus >= 201103L
237*38fd1498Szrj template<typename... _Args>
238*38fd1498Szrj iterator
239*38fd1498Szrj emplace(_Args&&... __args)
240*38fd1498Szrj {
241*38fd1498Szrj // The cost is the same whether or not the element is inserted so we
242*38fd1498Szrj // always report insertion of 1 element.
243*38fd1498Szrj __profcxx_map2umap_insert(this->_M_map2umap_info, this->size(), 1);
244*38fd1498Szrj return iterator(_Base::emplace(std::forward<_Args>(__args)...), this);
245*38fd1498Szrj }
246*38fd1498Szrj
247*38fd1498Szrj template<typename... _Args>
248*38fd1498Szrj iterator
249*38fd1498Szrj emplace_hint(const_iterator __pos, _Args&&... __args)
250*38fd1498Szrj {
251*38fd1498Szrj auto size_before = this->size();
252*38fd1498Szrj auto __res
253*38fd1498Szrj = _Base::emplace_hint(__pos.base(), std::forward<_Args>(__args)...);
254*38fd1498Szrj __profcxx_map2umap_insert(this->_M_map2umap_info,
255*38fd1498Szrj size_before, _M_hint_used(__pos.base(), __res) ? 0 : 1);
256*38fd1498Szrj return iterator(__res, this);
257*38fd1498Szrj }
258*38fd1498Szrj #endif
259*38fd1498Szrj
260*38fd1498Szrj iterator
261*38fd1498Szrj insert(const value_type& __x)
262*38fd1498Szrj {
263*38fd1498Szrj __profcxx_map2umap_insert(this->_M_map2umap_info, this->size(), 1);
264*38fd1498Szrj return iterator(_Base::insert(__x), this);
265*38fd1498Szrj }
266*38fd1498Szrj
267*38fd1498Szrj #if __cplusplus >= 201103L
268*38fd1498Szrj iterator
269*38fd1498Szrj insert(value_type&& __x)
270*38fd1498Szrj {
271*38fd1498Szrj __profcxx_map2umap_insert(this->_M_map2umap_info, this->size(), 1);
272*38fd1498Szrj return iterator(_Base::insert(std::move(__x)), this);
273*38fd1498Szrj }
274*38fd1498Szrj #endif
275*38fd1498Szrj
276*38fd1498Szrj iterator
277*38fd1498Szrj insert(const_iterator __pos, const value_type& __x)
278*38fd1498Szrj {
279*38fd1498Szrj size_type size_before = this->size();
280*38fd1498Szrj _Base_iterator __res = _Base::insert(__pos.base(), __x);
281*38fd1498Szrj
282*38fd1498Szrj __profcxx_map2umap_insert(this->_M_map2umap_info,
283*38fd1498Szrj size_before, _M_hint_used(__pos.base(), __res) ? 0 : 1);
284*38fd1498Szrj return iterator(__res, this);
285*38fd1498Szrj }
286*38fd1498Szrj
287*38fd1498Szrj #if __cplusplus >= 201103L
288*38fd1498Szrj iterator
289*38fd1498Szrj insert(const_iterator __pos, value_type&& __x)
290*38fd1498Szrj {
291*38fd1498Szrj auto size_before = this->size();
292*38fd1498Szrj auto __res = _Base::insert(__pos.base(), std::move(__x));
293*38fd1498Szrj __profcxx_map2umap_insert(this->_M_map2umap_info,
294*38fd1498Szrj size_before, _M_hint_used(__pos.base(), __res) ? 0 : 1);
295*38fd1498Szrj return iterator(__res, this);
296*38fd1498Szrj }
297*38fd1498Szrj #endif
298*38fd1498Szrj
299*38fd1498Szrj #if __cplusplus >= 201103L
300*38fd1498Szrj template<typename _InputIterator,
301*38fd1498Szrj typename = std::_RequireInputIter<_InputIterator>>
302*38fd1498Szrj #else
303*38fd1498Szrj template<typename _InputIterator>
304*38fd1498Szrj #endif
305*38fd1498Szrj void
306*38fd1498Szrj insert(_InputIterator __first, _InputIterator __last)
307*38fd1498Szrj {
308*38fd1498Szrj for (; __first != __last; ++__first)
309*38fd1498Szrj insert(*__first);
310*38fd1498Szrj }
311*38fd1498Szrj
312*38fd1498Szrj #if __cplusplus >= 201103L
313*38fd1498Szrj void
314*38fd1498Szrj insert(initializer_list<value_type> __l)
315*38fd1498Szrj { insert(__l.begin(), __l.end()); }
316*38fd1498Szrj #endif
317*38fd1498Szrj
318*38fd1498Szrj #if __cplusplus >= 201103L
319*38fd1498Szrj iterator
320*38fd1498Szrj erase(const_iterator __pos)
321*38fd1498Szrj {
322*38fd1498Szrj __profcxx_map2umap_erase(this->_M_map2umap_info, this->size(), 1);
323*38fd1498Szrj return iterator(_Base::erase(__pos.base()), this);
324*38fd1498Szrj }
325*38fd1498Szrj #else
326*38fd1498Szrj void
327*38fd1498Szrj erase(iterator __pos)
328*38fd1498Szrj {
329*38fd1498Szrj __profcxx_map2umap_erase(this->_M_map2umap_info, this->size(), 1);
330*38fd1498Szrj _Base::erase(__pos.base());
331*38fd1498Szrj }
332*38fd1498Szrj #endif
333*38fd1498Szrj
334*38fd1498Szrj size_type
335*38fd1498Szrj erase(const key_type& __x)
336*38fd1498Szrj {
337*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
338*38fd1498Szrj __profcxx_map2umap_erase(this->_M_map2umap_info, this->size(), 1);
339*38fd1498Szrj return _Base::erase(__x);
340*38fd1498Szrj }
341*38fd1498Szrj
342*38fd1498Szrj #if __cplusplus >= 201103L
343*38fd1498Szrj iterator
344*38fd1498Szrj erase(const_iterator __first, const_iterator __last)
345*38fd1498Szrj {
346*38fd1498Szrj if (__first != __last)
347*38fd1498Szrj {
348*38fd1498Szrj iterator __ret;
349*38fd1498Szrj for (; __first != __last;)
350*38fd1498Szrj __ret = erase(__first++);
351*38fd1498Szrj return __ret;
352*38fd1498Szrj }
353*38fd1498Szrj else
354*38fd1498Szrj return iterator(_Base::erase(__first.base(), __last.base()), this);
355*38fd1498Szrj }
356*38fd1498Szrj #else
357*38fd1498Szrj void
358*38fd1498Szrj erase(iterator __first, iterator __last)
359*38fd1498Szrj {
360*38fd1498Szrj for (; __first != __last;)
361*38fd1498Szrj erase(__first++);
362*38fd1498Szrj }
363*38fd1498Szrj #endif
364*38fd1498Szrj
365*38fd1498Szrj void
366*38fd1498Szrj clear() _GLIBCXX_NOEXCEPT
367*38fd1498Szrj {
368*38fd1498Szrj this->_M_profile_destruct();
369*38fd1498Szrj _Base::clear();
370*38fd1498Szrj this->_M_profile_construct();
371*38fd1498Szrj }
372*38fd1498Szrj
373*38fd1498Szrj size_type
374*38fd1498Szrj count(const key_type& __x) const
375*38fd1498Szrj {
376*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
377*38fd1498Szrj return _Base::count(__x);
378*38fd1498Szrj }
379*38fd1498Szrj
380*38fd1498Szrj #if __cplusplus > 201103L
381*38fd1498Szrj template<typename _Kt,
382*38fd1498Szrj typename _Req =
383*38fd1498Szrj typename __has_is_transparent<_Compare, _Kt>::type>
384*38fd1498Szrj size_type
385*38fd1498Szrj count(const _Kt& __x) const
386*38fd1498Szrj {
387*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
388*38fd1498Szrj return _Base::count(__x);
389*38fd1498Szrj }
390*38fd1498Szrj #endif
391*38fd1498Szrj
392*38fd1498Szrj // multiset operations:
393*38fd1498Szrj iterator
394*38fd1498Szrj find(const key_type& __x)
395*38fd1498Szrj {
396*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
397*38fd1498Szrj return iterator(_Base::find(__x), this);
398*38fd1498Szrj }
399*38fd1498Szrj
400*38fd1498Szrj // _GLIBCXX_RESOLVE_LIB_DEFECTS
401*38fd1498Szrj // 214. set::find() missing const overload
402*38fd1498Szrj const_iterator
403*38fd1498Szrj find(const key_type& __x) const
404*38fd1498Szrj {
405*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
406*38fd1498Szrj return const_iterator(_Base::find(__x), this);
407*38fd1498Szrj }
408*38fd1498Szrj
409*38fd1498Szrj #if __cplusplus > 201103L
410*38fd1498Szrj template<typename _Kt,
411*38fd1498Szrj typename _Req =
412*38fd1498Szrj typename __has_is_transparent<_Compare, _Kt>::type>
413*38fd1498Szrj iterator
414*38fd1498Szrj find(const _Kt& __x)
415*38fd1498Szrj {
416*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
417*38fd1498Szrj return { _Base::find(__x), this };
418*38fd1498Szrj }
419*38fd1498Szrj
420*38fd1498Szrj template<typename _Kt,
421*38fd1498Szrj typename _Req =
422*38fd1498Szrj typename __has_is_transparent<_Compare, _Kt>::type>
423*38fd1498Szrj const_iterator
424*38fd1498Szrj find(const _Kt& __x) const
425*38fd1498Szrj {
426*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
427*38fd1498Szrj return { _Base::find(__x), this };
428*38fd1498Szrj }
429*38fd1498Szrj #endif
430*38fd1498Szrj
431*38fd1498Szrj iterator
432*38fd1498Szrj lower_bound(const key_type& __x)
433*38fd1498Szrj {
434*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
435*38fd1498Szrj return iterator(_Base::lower_bound(__x), this);
436*38fd1498Szrj }
437*38fd1498Szrj
438*38fd1498Szrj // _GLIBCXX_RESOLVE_LIB_DEFECTS
439*38fd1498Szrj // 214. set::find() missing const overload
440*38fd1498Szrj const_iterator
441*38fd1498Szrj lower_bound(const key_type& __x) const
442*38fd1498Szrj {
443*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
444*38fd1498Szrj __profcxx_map2umap_invalidate(this->_M_map2umap_info);
445*38fd1498Szrj return const_iterator(_Base::lower_bound(__x), this);
446*38fd1498Szrj }
447*38fd1498Szrj
448*38fd1498Szrj #if __cplusplus > 201103L
449*38fd1498Szrj template<typename _Kt,
450*38fd1498Szrj typename _Req =
451*38fd1498Szrj typename __has_is_transparent<_Compare, _Kt>::type>
452*38fd1498Szrj iterator
453*38fd1498Szrj lower_bound(const _Kt& __x)
454*38fd1498Szrj {
455*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
456*38fd1498Szrj __profcxx_map2umap_invalidate(this->_M_map2umap_info);
457*38fd1498Szrj return { _Base::lower_bound(__x), this };
458*38fd1498Szrj }
459*38fd1498Szrj
460*38fd1498Szrj template<typename _Kt,
461*38fd1498Szrj typename _Req =
462*38fd1498Szrj typename __has_is_transparent<_Compare, _Kt>::type>
463*38fd1498Szrj const_iterator
464*38fd1498Szrj lower_bound(const _Kt& __x) const
465*38fd1498Szrj {
466*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
467*38fd1498Szrj __profcxx_map2umap_invalidate(this->_M_map2umap_info);
468*38fd1498Szrj return { _Base::lower_bound(__x), this };
469*38fd1498Szrj }
470*38fd1498Szrj #endif
471*38fd1498Szrj
472*38fd1498Szrj iterator
473*38fd1498Szrj upper_bound(const key_type& __x)
474*38fd1498Szrj {
475*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
476*38fd1498Szrj __profcxx_map2umap_invalidate(this->_M_map2umap_info);
477*38fd1498Szrj return iterator(_Base::upper_bound(__x), this);
478*38fd1498Szrj }
479*38fd1498Szrj
480*38fd1498Szrj // _GLIBCXX_RESOLVE_LIB_DEFECTS
481*38fd1498Szrj // 214. set::find() missing const overload
482*38fd1498Szrj const_iterator
483*38fd1498Szrj upper_bound(const key_type& __x) const
484*38fd1498Szrj {
485*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
486*38fd1498Szrj __profcxx_map2umap_invalidate(this->_M_map2umap_info);
487*38fd1498Szrj return const_iterator(_Base::upper_bound(__x), this);
488*38fd1498Szrj }
489*38fd1498Szrj
490*38fd1498Szrj #if __cplusplus > 201103L
491*38fd1498Szrj template<typename _Kt,
492*38fd1498Szrj typename _Req =
493*38fd1498Szrj typename __has_is_transparent<_Compare, _Kt>::type>
494*38fd1498Szrj iterator
495*38fd1498Szrj upper_bound(const _Kt& __x)
496*38fd1498Szrj {
497*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
498*38fd1498Szrj __profcxx_map2umap_invalidate(this->_M_map2umap_info);
499*38fd1498Szrj return { _Base::upper_bound(__x), this };
500*38fd1498Szrj }
501*38fd1498Szrj
502*38fd1498Szrj template<typename _Kt,
503*38fd1498Szrj typename _Req =
504*38fd1498Szrj typename __has_is_transparent<_Compare, _Kt>::type>
505*38fd1498Szrj const_iterator
506*38fd1498Szrj upper_bound(const _Kt& __x) const
507*38fd1498Szrj {
508*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
509*38fd1498Szrj __profcxx_map2umap_invalidate(this->_M_map2umap_info);
510*38fd1498Szrj return { _Base::upper_bound(__x), this };
511*38fd1498Szrj }
512*38fd1498Szrj #endif
513*38fd1498Szrj
514*38fd1498Szrj std::pair<iterator,iterator>
515*38fd1498Szrj equal_range(const key_type& __x)
516*38fd1498Szrj {
517*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
518*38fd1498Szrj std::pair<_Base_iterator, _Base_iterator> __base_ret
519*38fd1498Szrj = _Base::equal_range(__x);
520*38fd1498Szrj return std::make_pair(iterator(__base_ret.first, this),
521*38fd1498Szrj iterator(__base_ret.second, this));
522*38fd1498Szrj }
523*38fd1498Szrj
524*38fd1498Szrj // _GLIBCXX_RESOLVE_LIB_DEFECTS
525*38fd1498Szrj // 214. set::find() missing const overload
526*38fd1498Szrj std::pair<const_iterator,const_iterator>
527*38fd1498Szrj equal_range(const key_type& __x) const
528*38fd1498Szrj {
529*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
530*38fd1498Szrj std::pair<_Base_const_iterator, _Base_const_iterator> __base_ret
531*38fd1498Szrj = _Base::equal_range(__x);
532*38fd1498Szrj return std::make_pair(const_iterator(__base_ret.first, this),
533*38fd1498Szrj const_iterator(__base_ret.second, this));
534*38fd1498Szrj }
535*38fd1498Szrj
536*38fd1498Szrj #if __cplusplus > 201103L
537*38fd1498Szrj template<typename _Kt,
538*38fd1498Szrj typename _Req =
539*38fd1498Szrj typename __has_is_transparent<_Compare, _Kt>::type>
540*38fd1498Szrj std::pair<iterator, iterator>
541*38fd1498Szrj equal_range(const _Kt& __x)
542*38fd1498Szrj {
543*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
544*38fd1498Szrj auto __res = _Base::equal_range(__x);
545*38fd1498Szrj return { { __res.first, this }, { __res.second, this } };
546*38fd1498Szrj }
547*38fd1498Szrj
548*38fd1498Szrj template<typename _Kt,
549*38fd1498Szrj typename _Req =
550*38fd1498Szrj typename __has_is_transparent<_Compare, _Kt>::type>
551*38fd1498Szrj std::pair<const_iterator, const_iterator>
552*38fd1498Szrj equal_range(const _Kt& __x) const
553*38fd1498Szrj {
554*38fd1498Szrj __profcxx_map2umap_find(this->_M_map2umap_info, this->size());
555*38fd1498Szrj auto __res = _Base::equal_range(__x);
556*38fd1498Szrj return { { __res.first, this }, { __res.second, this } };
557*38fd1498Szrj }
558*38fd1498Szrj #endif
559*38fd1498Szrj
560*38fd1498Szrj _Base&
561*38fd1498Szrj _M_base() _GLIBCXX_NOEXCEPT { return *this; }
562*38fd1498Szrj
563*38fd1498Szrj const _Base&
564*38fd1498Szrj _M_base() const _GLIBCXX_NOEXCEPT { return *this; }
565*38fd1498Szrj
566*38fd1498Szrj private:
567*38fd1498Szrj /** If hint is used we consider that the map and unordered_map
568*38fd1498Szrj * operations have equivalent insertion cost so we do not update metrics
569*38fd1498Szrj * about it.
570*38fd1498Szrj * Note that to find out if hint has been used is libstdc++
571*38fd1498Szrj * implementation dependent.
572*38fd1498Szrj */
573*38fd1498Szrj bool
574*38fd1498Szrj _M_hint_used(_Base_const_iterator __hint, _Base_iterator __res)
575*38fd1498Szrj {
576*38fd1498Szrj return (__hint == __res
577*38fd1498Szrj || (__hint == _M_base().end() && ++__res == _M_base().end())
578*38fd1498Szrj || (__hint != _M_base().end() && (++__hint == __res
579*38fd1498Szrj || ++__res == --__hint)));
580*38fd1498Szrj }
581*38fd1498Szrj
582*38fd1498Szrj template<typename _K1, typename _C1, typename _A1>
583*38fd1498Szrj friend bool
584*38fd1498Szrj operator==(const multiset<_K1, _C1, _A1>&,
585*38fd1498Szrj const multiset<_K1, _C1, _A1>&);
586*38fd1498Szrj
587*38fd1498Szrj template<typename _K1, typename _C1, typename _A1>
588*38fd1498Szrj friend bool
589*38fd1498Szrj operator< (const multiset<_K1, _C1, _A1>&,
590*38fd1498Szrj const multiset<_K1, _C1, _A1>&);
591*38fd1498Szrj };
592*38fd1498Szrj
593*38fd1498Szrj template<typename _Key, typename _Compare, typename _Allocator>
594*38fd1498Szrj inline bool
595*38fd1498Szrj operator==(const multiset<_Key, _Compare, _Allocator>& __lhs,
596*38fd1498Szrj const multiset<_Key, _Compare, _Allocator>& __rhs)
597*38fd1498Szrj {
598*38fd1498Szrj __profcxx_map2umap_invalidate(__lhs._M_map2umap_info);
599*38fd1498Szrj __profcxx_map2umap_invalidate(__rhs._M_map2umap_info);
600*38fd1498Szrj return __lhs._M_base() == __rhs._M_base();
601*38fd1498Szrj }
602*38fd1498Szrj
603*38fd1498Szrj template<typename _Key, typename _Compare, typename _Allocator>
604*38fd1498Szrj inline bool
605*38fd1498Szrj operator<(const multiset<_Key, _Compare, _Allocator>& __lhs,
606*38fd1498Szrj const multiset<_Key, _Compare, _Allocator>& __rhs)
607*38fd1498Szrj {
608*38fd1498Szrj __profcxx_map2umap_invalidate(__lhs._M_map2umap_info);
609*38fd1498Szrj __profcxx_map2umap_invalidate(__rhs._M_map2umap_info);
610*38fd1498Szrj return __lhs._M_base() < __rhs._M_base();
611*38fd1498Szrj }
612*38fd1498Szrj
613*38fd1498Szrj template<typename _Key, typename _Compare, typename _Allocator>
614*38fd1498Szrj inline bool
615*38fd1498Szrj operator!=(const multiset<_Key, _Compare, _Allocator>& __lhs,
616*38fd1498Szrj const multiset<_Key, _Compare, _Allocator>& __rhs)
617*38fd1498Szrj { return !(__lhs == __rhs); }
618*38fd1498Szrj
619*38fd1498Szrj template<typename _Key, typename _Compare, typename _Allocator>
620*38fd1498Szrj inline bool
621*38fd1498Szrj operator<=(const multiset<_Key, _Compare, _Allocator>& __lhs,
622*38fd1498Szrj const multiset<_Key, _Compare, _Allocator>& __rhs)
623*38fd1498Szrj { return !(__rhs < __lhs); }
624*38fd1498Szrj
625*38fd1498Szrj template<typename _Key, typename _Compare, typename _Allocator>
626*38fd1498Szrj inline bool
627*38fd1498Szrj operator>=(const multiset<_Key, _Compare, _Allocator>& __lhs,
628*38fd1498Szrj const multiset<_Key, _Compare, _Allocator>& __rhs)
629*38fd1498Szrj { return !(__lhs < __rhs); }
630*38fd1498Szrj
631*38fd1498Szrj template<typename _Key, typename _Compare, typename _Allocator>
632*38fd1498Szrj inline bool
633*38fd1498Szrj operator>(const multiset<_Key, _Compare, _Allocator>& __lhs,
634*38fd1498Szrj const multiset<_Key, _Compare, _Allocator>& __rhs)
635*38fd1498Szrj { return __rhs < __lhs; }
636*38fd1498Szrj
637*38fd1498Szrj template<typename _Key, typename _Compare, typename _Allocator>
638*38fd1498Szrj void
639*38fd1498Szrj swap(multiset<_Key, _Compare, _Allocator>& __x,
640*38fd1498Szrj multiset<_Key, _Compare, _Allocator>& __y)
641*38fd1498Szrj _GLIBCXX_NOEXCEPT_IF(noexcept(__x.swap(__y)))
642*38fd1498Szrj { return __x.swap(__y); }
643*38fd1498Szrj
644*38fd1498Szrj } // namespace __profile
645*38fd1498Szrj } // namespace std
646*38fd1498Szrj
647*38fd1498Szrj #endif
648