• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1// -*- C++ -*-
2//===----------------------------- map ------------------------------------===//
3//
4//                     The LLVM Compiler Infrastructure
5//
6// This file is dual licensed under the MIT and the University of Illinois Open
7// Source Licenses. See LICENSE.TXT for details.
8//
9//===----------------------------------------------------------------------===//
10
11#ifndef _LIBCPP_MAP
12#define _LIBCPP_MAP
13
14/*
15
16    map synopsis
17
18namespace std
19{
20
21template <class Key, class T, class Compare = less<Key>,
22          class Allocator = allocator<pair<const Key, T>>>
23class map
24{
25public:
26    // types:
27    typedef Key                                      key_type;
28    typedef T                                        mapped_type;
29    typedef pair<const key_type, mapped_type>        value_type;
30    typedef Compare                                  key_compare;
31    typedef Allocator                                allocator_type;
32    typedef typename allocator_type::reference       reference;
33    typedef typename allocator_type::const_reference const_reference;
34    typedef typename allocator_type::pointer         pointer;
35    typedef typename allocator_type::const_pointer   const_pointer;
36    typedef typename allocator_type::size_type       size_type;
37    typedef typename allocator_type::difference_type difference_type;
38
39    typedef implementation-defined                   iterator;
40    typedef implementation-defined                   const_iterator;
41    typedef std::reverse_iterator<iterator>          reverse_iterator;
42    typedef std::reverse_iterator<const_iterator>    const_reverse_iterator;
43    typedef unspecified                              node_type;              // C++17
44    typedef INSERT_RETURN_TYPE<iterator, node_type>  insert_return_type;     // C++17
45
46    class value_compare
47        : public binary_function<value_type, value_type, bool>
48    {
49        friend class map;
50    protected:
51        key_compare comp;
52
53        value_compare(key_compare c);
54    public:
55        bool operator()(const value_type& x, const value_type& y) const;
56    };
57
58    // construct/copy/destroy:
59    map()
60        noexcept(
61            is_nothrow_default_constructible<allocator_type>::value &&
62            is_nothrow_default_constructible<key_compare>::value &&
63            is_nothrow_copy_constructible<key_compare>::value);
64    explicit map(const key_compare& comp);
65    map(const key_compare& comp, const allocator_type& a);
66    template <class InputIterator>
67        map(InputIterator first, InputIterator last,
68            const key_compare& comp = key_compare());
69    template <class InputIterator>
70        map(InputIterator first, InputIterator last,
71            const key_compare& comp, const allocator_type& a);
72    map(const map& m);
73    map(map&& m)
74        noexcept(
75            is_nothrow_move_constructible<allocator_type>::value &&
76            is_nothrow_move_constructible<key_compare>::value);
77    explicit map(const allocator_type& a);
78    map(const map& m, const allocator_type& a);
79    map(map&& m, const allocator_type& a);
80    map(initializer_list<value_type> il, const key_compare& comp = key_compare());
81    map(initializer_list<value_type> il, const key_compare& comp, const allocator_type& a);
82    template <class InputIterator>
83        map(InputIterator first, InputIterator last, const allocator_type& a)
84            : map(first, last, Compare(), a) {}  // C++14
85    map(initializer_list<value_type> il, const allocator_type& a)
86        : map(il, Compare(), a) {}  // C++14
87   ~map();
88
89    map& operator=(const map& m);
90    map& operator=(map&& m)
91        noexcept(
92            allocator_type::propagate_on_container_move_assignment::value &&
93            is_nothrow_move_assignable<allocator_type>::value &&
94            is_nothrow_move_assignable<key_compare>::value);
95    map& operator=(initializer_list<value_type> il);
96
97    // iterators:
98          iterator begin() noexcept;
99    const_iterator begin() const noexcept;
100          iterator end() noexcept;
101    const_iterator end()   const noexcept;
102
103          reverse_iterator rbegin() noexcept;
104    const_reverse_iterator rbegin() const noexcept;
105          reverse_iterator rend() noexcept;
106    const_reverse_iterator rend()   const noexcept;
107
108    const_iterator         cbegin()  const noexcept;
109    const_iterator         cend()    const noexcept;
110    const_reverse_iterator crbegin() const noexcept;
111    const_reverse_iterator crend()   const noexcept;
112
113    // capacity:
114    bool      empty()    const noexcept;
115    size_type size()     const noexcept;
116    size_type max_size() const noexcept;
117
118    // element access:
119    mapped_type& operator[](const key_type& k);
120    mapped_type& operator[](key_type&& k);
121
122          mapped_type& at(const key_type& k);
123    const mapped_type& at(const key_type& k) const;
124
125    // modifiers:
126    template <class... Args>
127        pair<iterator, bool> emplace(Args&&... args);
128    template <class... Args>
129        iterator emplace_hint(const_iterator position, Args&&... args);
130    pair<iterator, bool> insert(const value_type& v);
131    pair<iterator, bool> insert(      value_type&& v);                                // C++17
132    template <class P>
133        pair<iterator, bool> insert(P&& p);
134    iterator insert(const_iterator position, const value_type& v);
135    iterator insert(const_iterator position,       value_type&& v);                   // C++17
136    template <class P>
137        iterator insert(const_iterator position, P&& p);
138    template <class InputIterator>
139        void insert(InputIterator first, InputIterator last);
140    void insert(initializer_list<value_type> il);
141
142    node_type extract(const_iterator position);                                       // C++17
143    node_type extract(const key_type& x);                                             // C++17
144    insert_return_type insert(node_type&& nh);                                        // C++17
145    iterator insert(const_iterator hint, node_type&& nh);                             // C++17
146
147    template <class... Args>
148        pair<iterator, bool> try_emplace(const key_type& k, Args&&... args);          // C++17
149    template <class... Args>
150        pair<iterator, bool> try_emplace(key_type&& k, Args&&... args);               // C++17
151    template <class... Args>
152        iterator try_emplace(const_iterator hint, const key_type& k, Args&&... args); // C++17
153    template <class... Args>
154        iterator try_emplace(const_iterator hint, key_type&& k, Args&&... args);      // C++17
155    template <class M>
156        pair<iterator, bool> insert_or_assign(const key_type& k, M&& obj);            // C++17
157    template <class M>
158        pair<iterator, bool> insert_or_assign(key_type&& k, M&& obj);                 // C++17
159    template <class M>
160        iterator insert_or_assign(const_iterator hint, const key_type& k, M&& obj);   // C++17
161    template <class M>
162        iterator insert_or_assign(const_iterator hint, key_type&& k, M&& obj);        // C++17
163
164    iterator  erase(const_iterator position);
165    iterator  erase(iterator position); // C++14
166    size_type erase(const key_type& k);
167    iterator  erase(const_iterator first, const_iterator last);
168    void clear() noexcept;
169
170    template<class C2>
171      void merge(map<Key, T, C2, Allocator>& source);         // C++17
172    template<class C2>
173      void merge(map<Key, T, C2, Allocator>&& source);        // C++17
174    template<class C2>
175      void merge(multimap<Key, T, C2, Allocator>& source);    // C++17
176    template<class C2>
177      void merge(multimap<Key, T, C2, Allocator>&& source);   // C++17
178
179    void swap(map& m)
180        noexcept(allocator_traits<allocator_type>::is_always_equal::value &&
181            is_nothrow_swappable<key_compare>::value); // C++17
182
183    // observers:
184    allocator_type get_allocator() const noexcept;
185    key_compare    key_comp()      const;
186    value_compare  value_comp()    const;
187
188    // map operations:
189          iterator find(const key_type& k);
190    const_iterator find(const key_type& k) const;
191    template<typename K>
192        iterator find(const K& x);              // C++14
193    template<typename K>
194        const_iterator find(const K& x) const;  // C++14
195    template<typename K>
196      size_type count(const K& x) const;        // C++14
197
198    size_type      count(const key_type& k) const;
199          iterator lower_bound(const key_type& k);
200    const_iterator lower_bound(const key_type& k) const;
201    template<typename K>
202        iterator lower_bound(const K& x);              // C++14
203    template<typename K>
204        const_iterator lower_bound(const K& x) const;  // C++14
205
206          iterator upper_bound(const key_type& k);
207    const_iterator upper_bound(const key_type& k) const;
208    template<typename K>
209        iterator upper_bound(const K& x);              // C++14
210    template<typename K>
211        const_iterator upper_bound(const K& x) const;  // C++14
212
213    pair<iterator,iterator>             equal_range(const key_type& k);
214    pair<const_iterator,const_iterator> equal_range(const key_type& k) const;
215    template<typename K>
216        pair<iterator,iterator>             equal_range(const K& x);        // C++14
217    template<typename K>
218        pair<const_iterator,const_iterator> equal_range(const K& x) const;  // C++14
219};
220
221template <class Key, class T, class Compare, class Allocator>
222bool
223operator==(const map<Key, T, Compare, Allocator>& x,
224           const map<Key, T, Compare, Allocator>& y);
225
226template <class Key, class T, class Compare, class Allocator>
227bool
228operator< (const map<Key, T, Compare, Allocator>& x,
229           const map<Key, T, Compare, Allocator>& y);
230
231template <class Key, class T, class Compare, class Allocator>
232bool
233operator!=(const map<Key, T, Compare, Allocator>& x,
234           const map<Key, T, Compare, Allocator>& y);
235
236template <class Key, class T, class Compare, class Allocator>
237bool
238operator> (const map<Key, T, Compare, Allocator>& x,
239           const map<Key, T, Compare, Allocator>& y);
240
241template <class Key, class T, class Compare, class Allocator>
242bool
243operator>=(const map<Key, T, Compare, Allocator>& x,
244           const map<Key, T, Compare, Allocator>& y);
245
246template <class Key, class T, class Compare, class Allocator>
247bool
248operator<=(const map<Key, T, Compare, Allocator>& x,
249           const map<Key, T, Compare, Allocator>& y);
250
251// specialized algorithms:
252template <class Key, class T, class Compare, class Allocator>
253void
254swap(map<Key, T, Compare, Allocator>& x, map<Key, T, Compare, Allocator>& y)
255    noexcept(noexcept(x.swap(y)));
256
257template <class Key, class T, class Compare, class Allocator, class Predicate>
258  void erase_if(map<Key, T, Compare, Allocator>& c, Predicate pred);  // C++20
259
260
261template <class Key, class T, class Compare = less<Key>,
262          class Allocator = allocator<pair<const Key, T>>>
263class multimap
264{
265public:
266    // types:
267    typedef Key                                      key_type;
268    typedef T                                        mapped_type;
269    typedef pair<const key_type,mapped_type>         value_type;
270    typedef Compare                                  key_compare;
271    typedef Allocator                                allocator_type;
272    typedef typename allocator_type::reference       reference;
273    typedef typename allocator_type::const_reference const_reference;
274    typedef typename allocator_type::size_type       size_type;
275    typedef typename allocator_type::difference_type difference_type;
276    typedef typename allocator_type::pointer         pointer;
277    typedef typename allocator_type::const_pointer   const_pointer;
278
279    typedef implementation-defined                   iterator;
280    typedef implementation-defined                   const_iterator;
281    typedef std::reverse_iterator<iterator>          reverse_iterator;
282    typedef std::reverse_iterator<const_iterator>    const_reverse_iterator;
283    typedef unspecified                              node_type;              // C++17
284
285    class value_compare
286        : public binary_function<value_type,value_type,bool>
287    {
288        friend class multimap;
289    protected:
290        key_compare comp;
291        value_compare(key_compare c);
292    public:
293        bool operator()(const value_type& x, const value_type& y) const;
294    };
295
296    // construct/copy/destroy:
297    multimap()
298        noexcept(
299            is_nothrow_default_constructible<allocator_type>::value &&
300            is_nothrow_default_constructible<key_compare>::value &&
301            is_nothrow_copy_constructible<key_compare>::value);
302    explicit multimap(const key_compare& comp);
303    multimap(const key_compare& comp, const allocator_type& a);
304    template <class InputIterator>
305        multimap(InputIterator first, InputIterator last, const key_compare& comp);
306    template <class InputIterator>
307        multimap(InputIterator first, InputIterator last, const key_compare& comp,
308                 const allocator_type& a);
309    multimap(const multimap& m);
310    multimap(multimap&& m)
311        noexcept(
312            is_nothrow_move_constructible<allocator_type>::value &&
313            is_nothrow_move_constructible<key_compare>::value);
314    explicit multimap(const allocator_type& a);
315    multimap(const multimap& m, const allocator_type& a);
316    multimap(multimap&& m, const allocator_type& a);
317    multimap(initializer_list<value_type> il, const key_compare& comp = key_compare());
318    multimap(initializer_list<value_type> il, const key_compare& comp,
319             const allocator_type& a);
320    template <class InputIterator>
321        multimap(InputIterator first, InputIterator last, const allocator_type& a)
322            : multimap(first, last, Compare(), a) {} // C++14
323    multimap(initializer_list<value_type> il, const allocator_type& a)
324        : multimap(il, Compare(), a) {} // C++14
325    ~multimap();
326
327    multimap& operator=(const multimap& m);
328    multimap& operator=(multimap&& m)
329        noexcept(
330            allocator_type::propagate_on_container_move_assignment::value &&
331            is_nothrow_move_assignable<allocator_type>::value &&
332            is_nothrow_move_assignable<key_compare>::value);
333    multimap& operator=(initializer_list<value_type> il);
334
335    // iterators:
336          iterator begin() noexcept;
337    const_iterator begin() const noexcept;
338          iterator end() noexcept;
339    const_iterator end()   const noexcept;
340
341          reverse_iterator rbegin() noexcept;
342    const_reverse_iterator rbegin() const noexcept;
343          reverse_iterator rend() noexcept;
344    const_reverse_iterator rend()   const noexcept;
345
346    const_iterator         cbegin()  const noexcept;
347    const_iterator         cend()    const noexcept;
348    const_reverse_iterator crbegin() const noexcept;
349    const_reverse_iterator crend()   const noexcept;
350
351    // capacity:
352    bool      empty()    const noexcept;
353    size_type size()     const noexcept;
354    size_type max_size() const noexcept;
355
356    // modifiers:
357    template <class... Args>
358        iterator emplace(Args&&... args);
359    template <class... Args>
360        iterator emplace_hint(const_iterator position, Args&&... args);
361    iterator insert(const value_type& v);
362    iterator insert(      value_type&& v);                                            // C++17
363    template <class P>
364        iterator insert(P&& p);
365    iterator insert(const_iterator position, const value_type& v);
366    iterator insert(const_iterator position,       value_type&& v);                   // C++17
367    template <class P>
368        iterator insert(const_iterator position, P&& p);
369    template <class InputIterator>
370        void insert(InputIterator first, InputIterator last);
371    void insert(initializer_list<value_type> il);
372
373    node_type extract(const_iterator position);                                       // C++17
374    node_type extract(const key_type& x);                                             // C++17
375    iterator insert(node_type&& nh);                                                  // C++17
376    iterator insert(const_iterator hint, node_type&& nh);                             // C++17
377
378    iterator  erase(const_iterator position);
379    iterator  erase(iterator position); // C++14
380    size_type erase(const key_type& k);
381    iterator  erase(const_iterator first, const_iterator last);
382    void clear() noexcept;
383
384    template<class C2>
385      void merge(multimap<Key, T, C2, Allocator>& source);    // C++17
386    template<class C2>
387      void merge(multimap<Key, T, C2, Allocator>&& source);   // C++17
388    template<class C2>
389      void merge(map<Key, T, C2, Allocator>& source);         // C++17
390    template<class C2>
391      void merge(map<Key, T, C2, Allocator>&& source);        // C++17
392
393    void swap(multimap& m)
394        noexcept(allocator_traits<allocator_type>::is_always_equal::value &&
395            is_nothrow_swappable<key_compare>::value); // C++17
396
397    // observers:
398    allocator_type get_allocator() const noexcept;
399    key_compare    key_comp()      const;
400    value_compare  value_comp()    const;
401
402    // map operations:
403          iterator find(const key_type& k);
404    const_iterator find(const key_type& k) const;
405    template<typename K>
406        iterator find(const K& x);              // C++14
407    template<typename K>
408        const_iterator find(const K& x) const;  // C++14
409    template<typename K>
410      size_type count(const K& x) const;        // C++14
411
412    size_type      count(const key_type& k) const;
413          iterator lower_bound(const key_type& k);
414    const_iterator lower_bound(const key_type& k) const;
415    template<typename K>
416        iterator lower_bound(const K& x);              // C++14
417    template<typename K>
418        const_iterator lower_bound(const K& x) const;  // C++14
419
420          iterator upper_bound(const key_type& k);
421    const_iterator upper_bound(const key_type& k) const;
422    template<typename K>
423        iterator upper_bound(const K& x);              // C++14
424    template<typename K>
425        const_iterator upper_bound(const K& x) const;  // C++14
426
427    pair<iterator,iterator>             equal_range(const key_type& k);
428    pair<const_iterator,const_iterator> equal_range(const key_type& k) const;
429    template<typename K>
430        pair<iterator,iterator>             equal_range(const K& x);        // C++14
431    template<typename K>
432        pair<const_iterator,const_iterator> equal_range(const K& x) const;  // C++14
433};
434
435template <class Key, class T, class Compare, class Allocator>
436bool
437operator==(const multimap<Key, T, Compare, Allocator>& x,
438           const multimap<Key, T, Compare, Allocator>& y);
439
440template <class Key, class T, class Compare, class Allocator>
441bool
442operator< (const multimap<Key, T, Compare, Allocator>& x,
443           const multimap<Key, T, Compare, Allocator>& y);
444
445template <class Key, class T, class Compare, class Allocator>
446bool
447operator!=(const multimap<Key, T, Compare, Allocator>& x,
448           const multimap<Key, T, Compare, Allocator>& y);
449
450template <class Key, class T, class Compare, class Allocator>
451bool
452operator> (const multimap<Key, T, Compare, Allocator>& x,
453           const multimap<Key, T, Compare, Allocator>& y);
454
455template <class Key, class T, class Compare, class Allocator>
456bool
457operator>=(const multimap<Key, T, Compare, Allocator>& x,
458           const multimap<Key, T, Compare, Allocator>& y);
459
460template <class Key, class T, class Compare, class Allocator>
461bool
462operator<=(const multimap<Key, T, Compare, Allocator>& x,
463           const multimap<Key, T, Compare, Allocator>& y);
464
465// specialized algorithms:
466template <class Key, class T, class Compare, class Allocator>
467void
468swap(multimap<Key, T, Compare, Allocator>& x,
469     multimap<Key, T, Compare, Allocator>& y)
470    noexcept(noexcept(x.swap(y)));
471
472template <class Key, class T, class Compare, class Allocator, class Predicate>
473  void erase_if(multimap<Key, T, Compare, Allocator>& c, Predicate pred);  // C++20
474
475}  // std
476
477*/
478
479#include <__config>
480#include <__tree>
481#include <__node_handle>
482#include <iterator>
483#include <memory>
484#include <utility>
485#include <functional>
486#include <initializer_list>
487#include <type_traits>
488#include <version>
489
490#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
491#pragma GCC system_header
492#endif
493
494_LIBCPP_BEGIN_NAMESPACE_STD
495
496template <class _Key, class _CP, class _Compare,
497          bool = is_empty<_Compare>::value && !__libcpp_is_final<_Compare>::value>
498class __map_value_compare
499    : private _Compare
500{
501public:
502    _LIBCPP_INLINE_VISIBILITY
503    __map_value_compare()
504        _NOEXCEPT_(is_nothrow_default_constructible<_Compare>::value)
505        : _Compare() {}
506    _LIBCPP_INLINE_VISIBILITY
507    __map_value_compare(_Compare c)
508        _NOEXCEPT_(is_nothrow_copy_constructible<_Compare>::value)
509        : _Compare(c) {}
510    _LIBCPP_INLINE_VISIBILITY
511    const _Compare& key_comp() const _NOEXCEPT {return *this;}
512    _LIBCPP_INLINE_VISIBILITY
513    bool operator()(const _CP& __x, const _CP& __y) const
514        {return static_cast<const _Compare&>(*this)(__x.__get_value().first, __y.__get_value().first);}
515    _LIBCPP_INLINE_VISIBILITY
516    bool operator()(const _CP& __x, const _Key& __y) const
517        {return static_cast<const _Compare&>(*this)(__x.__get_value().first, __y);}
518    _LIBCPP_INLINE_VISIBILITY
519    bool operator()(const _Key& __x, const _CP& __y) const
520        {return static_cast<const _Compare&>(*this)(__x, __y.__get_value().first);}
521    void swap(__map_value_compare&__y)
522        _NOEXCEPT_(__is_nothrow_swappable<_Compare>::value)
523    {
524      using _VSTD::swap;
525      swap(static_cast<_Compare&>(*this), static_cast<_Compare&>(__y));
526    }
527
528#if _LIBCPP_STD_VER > 11
529    template <typename _K2>
530    _LIBCPP_INLINE_VISIBILITY
531    typename enable_if<__is_transparent<_Compare, _K2>::value, bool>::type
532    operator () ( const _K2& __x, const _CP& __y ) const
533        {return static_cast<const _Compare&>(*this) (__x, __y.__get_value().first);}
534
535    template <typename _K2>
536    _LIBCPP_INLINE_VISIBILITY
537    typename enable_if<__is_transparent<_Compare, _K2>::value, bool>::type
538    operator () (const _CP& __x, const _K2& __y) const
539        {return static_cast<const _Compare&>(*this) (__x.__get_value().first, __y);}
540#endif
541};
542
543template <class _Key, class _CP, class _Compare>
544class __map_value_compare<_Key, _CP, _Compare, false>
545{
546    _Compare comp;
547
548public:
549    _LIBCPP_INLINE_VISIBILITY
550    __map_value_compare()
551        _NOEXCEPT_(is_nothrow_default_constructible<_Compare>::value)
552        : comp() {}
553    _LIBCPP_INLINE_VISIBILITY
554    __map_value_compare(_Compare c)
555        _NOEXCEPT_(is_nothrow_copy_constructible<_Compare>::value)
556        : comp(c) {}
557    _LIBCPP_INLINE_VISIBILITY
558    const _Compare& key_comp() const _NOEXCEPT {return comp;}
559
560    _LIBCPP_INLINE_VISIBILITY
561    bool operator()(const _CP& __x, const _CP& __y) const
562        {return comp(__x.__get_value().first, __y.__get_value().first);}
563    _LIBCPP_INLINE_VISIBILITY
564    bool operator()(const _CP& __x, const _Key& __y) const
565        {return comp(__x.__get_value().first, __y);}
566    _LIBCPP_INLINE_VISIBILITY
567    bool operator()(const _Key& __x, const _CP& __y) const
568        {return comp(__x, __y.__get_value().first);}
569    void swap(__map_value_compare&__y)
570        _NOEXCEPT_(__is_nothrow_swappable<_Compare>::value)
571    {
572        using _VSTD::swap;
573        swap(comp, __y.comp);
574    }
575
576#if _LIBCPP_STD_VER > 11
577    template <typename _K2>
578    _LIBCPP_INLINE_VISIBILITY
579    typename enable_if<__is_transparent<_Compare, _K2>::value, bool>::type
580    operator () ( const _K2& __x, const _CP& __y ) const
581        {return comp (__x, __y.__get_value().first);}
582
583    template <typename _K2>
584    _LIBCPP_INLINE_VISIBILITY
585    typename enable_if<__is_transparent<_Compare, _K2>::value, bool>::type
586    operator () (const _CP& __x, const _K2& __y) const
587        {return comp (__x.__get_value().first, __y);}
588#endif
589};
590
591template <class _Key, class _CP, class _Compare, bool __b>
592inline _LIBCPP_INLINE_VISIBILITY
593void
594swap(__map_value_compare<_Key, _CP, _Compare, __b>& __x,
595     __map_value_compare<_Key, _CP, _Compare, __b>& __y)
596    _NOEXCEPT_(_NOEXCEPT_(__x.swap(__y)))
597{
598    __x.swap(__y);
599}
600
601template <class _Allocator>
602class __map_node_destructor
603{
604    typedef _Allocator                          allocator_type;
605    typedef allocator_traits<allocator_type>    __alloc_traits;
606
607public:
608    typedef typename __alloc_traits::pointer    pointer;
609
610private:
611    allocator_type& __na_;
612
613    __map_node_destructor& operator=(const __map_node_destructor&);
614
615public:
616    bool __first_constructed;
617    bool __second_constructed;
618
619    _LIBCPP_INLINE_VISIBILITY
620    explicit __map_node_destructor(allocator_type& __na) _NOEXCEPT
621        : __na_(__na),
622          __first_constructed(false),
623          __second_constructed(false)
624        {}
625
626#ifndef _LIBCPP_CXX03_LANG
627    _LIBCPP_INLINE_VISIBILITY
628    __map_node_destructor(__tree_node_destructor<allocator_type>&& __x) _NOEXCEPT
629        : __na_(__x.__na_),
630          __first_constructed(__x.__value_constructed),
631          __second_constructed(__x.__value_constructed)
632        {
633            __x.__value_constructed = false;
634        }
635#endif  // _LIBCPP_CXX03_LANG
636
637    _LIBCPP_INLINE_VISIBILITY
638    void operator()(pointer __p) _NOEXCEPT
639    {
640        if (__second_constructed)
641            __alloc_traits::destroy(__na_, _VSTD::addressof(__p->__value_.__get_value().second));
642        if (__first_constructed)
643            __alloc_traits::destroy(__na_, _VSTD::addressof(__p->__value_.__get_value().first));
644        if (__p)
645            __alloc_traits::deallocate(__na_, __p, 1);
646    }
647};
648
649template <class _Key, class _Tp, class _Compare, class _Allocator>
650    class map;
651template <class _Key, class _Tp, class _Compare, class _Allocator>
652    class multimap;
653template <class _TreeIterator> class __map_const_iterator;
654
655#ifndef _LIBCPP_CXX03_LANG
656
657template <class _Key, class _Tp>
658struct __value_type
659{
660    typedef _Key                                     key_type;
661    typedef _Tp                                      mapped_type;
662    typedef pair<const key_type, mapped_type>        value_type;
663    typedef pair<key_type&, mapped_type&>            __nc_ref_pair_type;
664    typedef pair<key_type&&, mapped_type&&>          __nc_rref_pair_type;
665
666private:
667    value_type __cc;
668
669public:
670    _LIBCPP_INLINE_VISIBILITY
671    value_type& __get_value()
672    {
673#if _LIBCPP_STD_VER > 14
674        return *_VSTD::launder(_VSTD::addressof(__cc));
675#else
676        return __cc;
677#endif
678    }
679
680    _LIBCPP_INLINE_VISIBILITY
681    const value_type& __get_value() const
682    {
683#if _LIBCPP_STD_VER > 14
684        return *_VSTD::launder(_VSTD::addressof(__cc));
685#else
686        return __cc;
687#endif
688    }
689
690    _LIBCPP_INLINE_VISIBILITY
691    __nc_ref_pair_type __ref()
692    {
693        value_type& __v = __get_value();
694        return __nc_ref_pair_type(const_cast<key_type&>(__v.first), __v.second);
695    }
696
697    _LIBCPP_INLINE_VISIBILITY
698    __nc_rref_pair_type __move()
699    {
700        value_type& __v = __get_value();
701        return __nc_rref_pair_type(
702            _VSTD::move(const_cast<key_type&>(__v.first)),
703            _VSTD::move(__v.second));
704    }
705
706    _LIBCPP_INLINE_VISIBILITY
707    __value_type& operator=(const __value_type& __v)
708    {
709        __ref() = __v.__get_value();
710        return *this;
711    }
712
713    _LIBCPP_INLINE_VISIBILITY
714    __value_type& operator=(__value_type&& __v)
715    {
716        __ref() = __v.__move();
717        return *this;
718    }
719
720    template <class _ValueTp,
721              class = typename enable_if<
722                    __is_same_uncvref<_ValueTp, value_type>::value
723                 >::type
724             >
725    _LIBCPP_INLINE_VISIBILITY
726    __value_type& operator=(_ValueTp&& __v)
727    {
728        __ref() = _VSTD::forward<_ValueTp>(__v);
729        return *this;
730    }
731
732private:
733    __value_type() _LIBCPP_EQUAL_DELETE;
734    ~__value_type() _LIBCPP_EQUAL_DELETE;
735    __value_type(const __value_type& __v) _LIBCPP_EQUAL_DELETE;
736    __value_type(__value_type&& __v) _LIBCPP_EQUAL_DELETE;
737};
738
739#else
740
741template <class _Key, class _Tp>
742struct __value_type
743{
744    typedef _Key                                     key_type;
745    typedef _Tp                                      mapped_type;
746    typedef pair<const key_type, mapped_type>        value_type;
747
748private:
749    value_type __cc;
750
751public:
752    _LIBCPP_INLINE_VISIBILITY
753    value_type& __get_value() { return __cc; }
754    _LIBCPP_INLINE_VISIBILITY
755    const value_type& __get_value() const { return __cc; }
756
757private:
758   __value_type();
759   __value_type(__value_type const&);
760   __value_type& operator=(__value_type const&);
761   ~__value_type();
762};
763
764#endif // _LIBCPP_CXX03_LANG
765
766template <class _Tp>
767struct __extract_key_value_types;
768
769template <class _Key, class _Tp>
770struct __extract_key_value_types<__value_type<_Key, _Tp> >
771{
772  typedef _Key const __key_type;
773  typedef _Tp        __mapped_type;
774};
775
776template <class _TreeIterator>
777class _LIBCPP_TEMPLATE_VIS __map_iterator
778{
779    typedef typename _TreeIterator::_NodeTypes                   _NodeTypes;
780    typedef typename _TreeIterator::__pointer_traits             __pointer_traits;
781
782    _TreeIterator __i_;
783
784public:
785    typedef bidirectional_iterator_tag                           iterator_category;
786    typedef typename _NodeTypes::__map_value_type                value_type;
787    typedef typename _TreeIterator::difference_type              difference_type;
788    typedef value_type&                                          reference;
789    typedef typename _NodeTypes::__map_value_type_pointer        pointer;
790
791    _LIBCPP_INLINE_VISIBILITY
792    __map_iterator() _NOEXCEPT {}
793
794    _LIBCPP_INLINE_VISIBILITY
795    __map_iterator(_TreeIterator __i) _NOEXCEPT : __i_(__i) {}
796
797    _LIBCPP_INLINE_VISIBILITY
798    reference operator*() const {return __i_->__get_value();}
799    _LIBCPP_INLINE_VISIBILITY
800    pointer operator->() const {return pointer_traits<pointer>::pointer_to(__i_->__get_value());}
801
802    _LIBCPP_INLINE_VISIBILITY
803    __map_iterator& operator++() {++__i_; return *this;}
804    _LIBCPP_INLINE_VISIBILITY
805    __map_iterator operator++(int)
806    {
807        __map_iterator __t(*this);
808        ++(*this);
809        return __t;
810    }
811
812    _LIBCPP_INLINE_VISIBILITY
813    __map_iterator& operator--() {--__i_; return *this;}
814    _LIBCPP_INLINE_VISIBILITY
815    __map_iterator operator--(int)
816    {
817        __map_iterator __t(*this);
818        --(*this);
819        return __t;
820    }
821
822    friend _LIBCPP_INLINE_VISIBILITY
823    bool operator==(const __map_iterator& __x, const __map_iterator& __y)
824        {return __x.__i_ == __y.__i_;}
825    friend
826    _LIBCPP_INLINE_VISIBILITY
827    bool operator!=(const __map_iterator& __x, const __map_iterator& __y)
828        {return __x.__i_ != __y.__i_;}
829
830    template <class, class, class, class> friend class _LIBCPP_TEMPLATE_VIS map;
831    template <class, class, class, class> friend class _LIBCPP_TEMPLATE_VIS multimap;
832    template <class> friend class _LIBCPP_TEMPLATE_VIS __map_const_iterator;
833};
834
835template <class _TreeIterator>
836class _LIBCPP_TEMPLATE_VIS __map_const_iterator
837{
838    typedef typename _TreeIterator::_NodeTypes                   _NodeTypes;
839    typedef typename _TreeIterator::__pointer_traits             __pointer_traits;
840
841    _TreeIterator __i_;
842
843public:
844    typedef bidirectional_iterator_tag                           iterator_category;
845    typedef typename _NodeTypes::__map_value_type                value_type;
846    typedef typename _TreeIterator::difference_type              difference_type;
847    typedef const value_type&                                    reference;
848    typedef typename _NodeTypes::__const_map_value_type_pointer  pointer;
849
850    _LIBCPP_INLINE_VISIBILITY
851    __map_const_iterator() _NOEXCEPT {}
852
853    _LIBCPP_INLINE_VISIBILITY
854    __map_const_iterator(_TreeIterator __i) _NOEXCEPT : __i_(__i) {}
855    _LIBCPP_INLINE_VISIBILITY
856    __map_const_iterator(__map_iterator<
857        typename _TreeIterator::__non_const_iterator> __i) _NOEXCEPT
858        : __i_(__i.__i_) {}
859
860    _LIBCPP_INLINE_VISIBILITY
861    reference operator*() const {return __i_->__get_value();}
862    _LIBCPP_INLINE_VISIBILITY
863    pointer operator->() const {return pointer_traits<pointer>::pointer_to(__i_->__get_value());}
864
865    _LIBCPP_INLINE_VISIBILITY
866    __map_const_iterator& operator++() {++__i_; return *this;}
867    _LIBCPP_INLINE_VISIBILITY
868    __map_const_iterator operator++(int)
869    {
870        __map_const_iterator __t(*this);
871        ++(*this);
872        return __t;
873    }
874
875    _LIBCPP_INLINE_VISIBILITY
876    __map_const_iterator& operator--() {--__i_; return *this;}
877    _LIBCPP_INLINE_VISIBILITY
878    __map_const_iterator operator--(int)
879    {
880        __map_const_iterator __t(*this);
881        --(*this);
882        return __t;
883    }
884
885    friend _LIBCPP_INLINE_VISIBILITY
886    bool operator==(const __map_const_iterator& __x, const __map_const_iterator& __y)
887        {return __x.__i_ == __y.__i_;}
888    friend _LIBCPP_INLINE_VISIBILITY
889    bool operator!=(const __map_const_iterator& __x, const __map_const_iterator& __y)
890        {return __x.__i_ != __y.__i_;}
891
892    template <class, class, class, class> friend class _LIBCPP_TEMPLATE_VIS map;
893    template <class, class, class, class> friend class _LIBCPP_TEMPLATE_VIS multimap;
894    template <class, class, class> friend class _LIBCPP_TEMPLATE_VIS __tree_const_iterator;
895};
896
897template <class _Key, class _Tp, class _Compare = less<_Key>,
898          class _Allocator = allocator<pair<const _Key, _Tp> > >
899class _LIBCPP_TEMPLATE_VIS map
900{
901public:
902    // types:
903    typedef _Key                                     key_type;
904    typedef _Tp                                      mapped_type;
905    typedef pair<const key_type, mapped_type>        value_type;
906    typedef _Compare                                 key_compare;
907    typedef _Allocator                               allocator_type;
908    typedef value_type&                              reference;
909    typedef const value_type&                        const_reference;
910
911    static_assert(sizeof(__diagnose_non_const_comparator<_Key, _Compare>()), "");
912    static_assert((is_same<typename allocator_type::value_type, value_type>::value),
913                  "Allocator::value_type must be same type as value_type");
914
915    class _LIBCPP_TEMPLATE_VIS value_compare
916        : public binary_function<value_type, value_type, bool>
917    {
918        friend class map;
919    protected:
920        key_compare comp;
921
922        _LIBCPP_INLINE_VISIBILITY value_compare(key_compare c) : comp(c) {}
923    public:
924        _LIBCPP_INLINE_VISIBILITY
925        bool operator()(const value_type& __x, const value_type& __y) const
926            {return comp(__x.first, __y.first);}
927    };
928
929private:
930
931    typedef _VSTD::__value_type<key_type, mapped_type>             __value_type;
932    typedef __map_value_compare<key_type, __value_type, key_compare> __vc;
933    typedef typename __rebind_alloc_helper<allocator_traits<allocator_type>,
934                                                 __value_type>::type __allocator_type;
935    typedef __tree<__value_type, __vc, __allocator_type>   __base;
936    typedef typename __base::__node_traits                 __node_traits;
937    typedef allocator_traits<allocator_type>               __alloc_traits;
938
939    __base __tree_;
940
941public:
942    typedef typename __alloc_traits::pointer               pointer;
943    typedef typename __alloc_traits::const_pointer         const_pointer;
944    typedef typename __alloc_traits::size_type             size_type;
945    typedef typename __alloc_traits::difference_type       difference_type;
946    typedef __map_iterator<typename __base::iterator>             iterator;
947    typedef __map_const_iterator<typename __base::const_iterator> const_iterator;
948    typedef _VSTD::reverse_iterator<iterator>               reverse_iterator;
949    typedef _VSTD::reverse_iterator<const_iterator>         const_reverse_iterator;
950
951#if _LIBCPP_STD_VER > 14
952    typedef __map_node_handle<typename __base::__node, allocator_type> node_type;
953    typedef __insert_return_type<iterator, node_type> insert_return_type;
954#endif
955
956    template <class _Key2, class _Value2, class _Comp2, class _Alloc2>
957        friend class _LIBCPP_TEMPLATE_VIS map;
958    template <class _Key2, class _Value2, class _Comp2, class _Alloc2>
959        friend class _LIBCPP_TEMPLATE_VIS multimap;
960
961    _LIBCPP_INLINE_VISIBILITY
962    map()
963        _NOEXCEPT_(
964            is_nothrow_default_constructible<allocator_type>::value &&
965            is_nothrow_default_constructible<key_compare>::value &&
966            is_nothrow_copy_constructible<key_compare>::value)
967        : __tree_(__vc(key_compare())) {}
968
969    _LIBCPP_INLINE_VISIBILITY
970    explicit map(const key_compare& __comp)
971        _NOEXCEPT_(
972            is_nothrow_default_constructible<allocator_type>::value &&
973            is_nothrow_copy_constructible<key_compare>::value)
974        : __tree_(__vc(__comp)) {}
975
976    _LIBCPP_INLINE_VISIBILITY
977    explicit map(const key_compare& __comp, const allocator_type& __a)
978        : __tree_(__vc(__comp), typename __base::allocator_type(__a)) {}
979
980    template <class _InputIterator>
981    _LIBCPP_INLINE_VISIBILITY
982        map(_InputIterator __f, _InputIterator __l,
983            const key_compare& __comp = key_compare())
984        : __tree_(__vc(__comp))
985        {
986            insert(__f, __l);
987        }
988
989    template <class _InputIterator>
990    _LIBCPP_INLINE_VISIBILITY
991        map(_InputIterator __f, _InputIterator __l,
992            const key_compare& __comp, const allocator_type& __a)
993        : __tree_(__vc(__comp), typename __base::allocator_type(__a))
994        {
995            insert(__f, __l);
996        }
997
998#if _LIBCPP_STD_VER > 11
999    template <class _InputIterator>
1000    _LIBCPP_INLINE_VISIBILITY
1001    map(_InputIterator __f, _InputIterator __l, const allocator_type& __a)
1002        : map(__f, __l, key_compare(), __a) {}
1003#endif
1004
1005    _LIBCPP_INLINE_VISIBILITY
1006    map(const map& __m)
1007        : __tree_(__m.__tree_)
1008        {
1009            insert(__m.begin(), __m.end());
1010        }
1011
1012    _LIBCPP_INLINE_VISIBILITY
1013    map& operator=(const map& __m)
1014        {
1015#ifndef _LIBCPP_CXX03_LANG
1016            __tree_ = __m.__tree_;
1017#else
1018            if (this != &__m) {
1019                __tree_.clear();
1020                __tree_.value_comp() = __m.__tree_.value_comp();
1021                __tree_.__copy_assign_alloc(__m.__tree_);
1022                insert(__m.begin(), __m.end());
1023            }
1024#endif
1025            return *this;
1026        }
1027
1028#ifndef _LIBCPP_CXX03_LANG
1029
1030    _LIBCPP_INLINE_VISIBILITY
1031    map(map&& __m)
1032        _NOEXCEPT_(is_nothrow_move_constructible<__base>::value)
1033        : __tree_(_VSTD::move(__m.__tree_))
1034        {
1035        }
1036
1037    map(map&& __m, const allocator_type& __a);
1038
1039    _LIBCPP_INLINE_VISIBILITY
1040    map& operator=(map&& __m)
1041        _NOEXCEPT_(is_nothrow_move_assignable<__base>::value)
1042        {
1043            __tree_ = _VSTD::move(__m.__tree_);
1044            return *this;
1045        }
1046
1047    _LIBCPP_INLINE_VISIBILITY
1048    map(initializer_list<value_type> __il, const key_compare& __comp = key_compare())
1049        : __tree_(__vc(__comp))
1050        {
1051            insert(__il.begin(), __il.end());
1052        }
1053
1054    _LIBCPP_INLINE_VISIBILITY
1055    map(initializer_list<value_type> __il, const key_compare& __comp, const allocator_type& __a)
1056        : __tree_(__vc(__comp), typename __base::allocator_type(__a))
1057        {
1058            insert(__il.begin(), __il.end());
1059        }
1060
1061#if _LIBCPP_STD_VER > 11
1062    _LIBCPP_INLINE_VISIBILITY
1063    map(initializer_list<value_type> __il, const allocator_type& __a)
1064        : map(__il, key_compare(), __a) {}
1065#endif
1066
1067    _LIBCPP_INLINE_VISIBILITY
1068    map& operator=(initializer_list<value_type> __il)
1069        {
1070            __tree_.__assign_unique(__il.begin(), __il.end());
1071            return *this;
1072        }
1073
1074#endif  // _LIBCPP_CXX03_LANG
1075
1076    _LIBCPP_INLINE_VISIBILITY
1077    explicit map(const allocator_type& __a)
1078        : __tree_(typename __base::allocator_type(__a))
1079        {
1080        }
1081
1082    _LIBCPP_INLINE_VISIBILITY
1083    map(const map& __m, const allocator_type& __a)
1084        : __tree_(__m.__tree_.value_comp(), typename __base::allocator_type(__a))
1085        {
1086            insert(__m.begin(), __m.end());
1087        }
1088
1089    _LIBCPP_INLINE_VISIBILITY
1090          iterator begin() _NOEXCEPT {return __tree_.begin();}
1091    _LIBCPP_INLINE_VISIBILITY
1092    const_iterator begin() const _NOEXCEPT {return __tree_.begin();}
1093    _LIBCPP_INLINE_VISIBILITY
1094          iterator end() _NOEXCEPT {return __tree_.end();}
1095    _LIBCPP_INLINE_VISIBILITY
1096    const_iterator end() const _NOEXCEPT {return __tree_.end();}
1097
1098    _LIBCPP_INLINE_VISIBILITY
1099          reverse_iterator rbegin() _NOEXCEPT {return reverse_iterator(end());}
1100    _LIBCPP_INLINE_VISIBILITY
1101    const_reverse_iterator rbegin() const _NOEXCEPT
1102        {return const_reverse_iterator(end());}
1103    _LIBCPP_INLINE_VISIBILITY
1104          reverse_iterator rend() _NOEXCEPT
1105            {return       reverse_iterator(begin());}
1106    _LIBCPP_INLINE_VISIBILITY
1107    const_reverse_iterator rend() const _NOEXCEPT
1108        {return const_reverse_iterator(begin());}
1109
1110    _LIBCPP_INLINE_VISIBILITY
1111    const_iterator cbegin() const _NOEXCEPT {return begin();}
1112    _LIBCPP_INLINE_VISIBILITY
1113    const_iterator cend() const _NOEXCEPT {return end();}
1114    _LIBCPP_INLINE_VISIBILITY
1115    const_reverse_iterator crbegin() const _NOEXCEPT {return rbegin();}
1116    _LIBCPP_INLINE_VISIBILITY
1117    const_reverse_iterator crend() const _NOEXCEPT {return rend();}
1118
1119    _LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_INLINE_VISIBILITY
1120    bool      empty() const _NOEXCEPT {return __tree_.size() == 0;}
1121    _LIBCPP_INLINE_VISIBILITY
1122    size_type size() const _NOEXCEPT {return __tree_.size();}
1123    _LIBCPP_INLINE_VISIBILITY
1124    size_type max_size() const _NOEXCEPT {return __tree_.max_size();}
1125
1126    mapped_type& operator[](const key_type& __k);
1127#ifndef _LIBCPP_CXX03_LANG
1128    mapped_type& operator[](key_type&& __k);
1129#endif
1130
1131          mapped_type& at(const key_type& __k);
1132    const mapped_type& at(const key_type& __k) const;
1133
1134    _LIBCPP_INLINE_VISIBILITY
1135    allocator_type get_allocator() const _NOEXCEPT {return allocator_type(__tree_.__alloc());}
1136    _LIBCPP_INLINE_VISIBILITY
1137    key_compare    key_comp()      const {return __tree_.value_comp().key_comp();}
1138    _LIBCPP_INLINE_VISIBILITY
1139    value_compare  value_comp()    const {return value_compare(__tree_.value_comp().key_comp());}
1140
1141#ifndef _LIBCPP_CXX03_LANG
1142    template <class ..._Args>
1143    _LIBCPP_INLINE_VISIBILITY
1144    pair<iterator, bool> emplace(_Args&& ...__args) {
1145        return __tree_.__emplace_unique(_VSTD::forward<_Args>(__args)...);
1146    }
1147
1148    template <class ..._Args>
1149    _LIBCPP_INLINE_VISIBILITY
1150    iterator emplace_hint(const_iterator __p, _Args&& ...__args) {
1151        return __tree_.__emplace_hint_unique(__p.__i_, _VSTD::forward<_Args>(__args)...);
1152    }
1153
1154    template <class _Pp,
1155              class = typename enable_if<is_constructible<value_type, _Pp>::value>::type>
1156        _LIBCPP_INLINE_VISIBILITY
1157        pair<iterator, bool> insert(_Pp&& __p)
1158            {return __tree_.__insert_unique(_VSTD::forward<_Pp>(__p));}
1159
1160    template <class _Pp,
1161              class = typename enable_if<is_constructible<value_type, _Pp>::value>::type>
1162        _LIBCPP_INLINE_VISIBILITY
1163        iterator insert(const_iterator __pos, _Pp&& __p)
1164            {return __tree_.__insert_unique(__pos.__i_, _VSTD::forward<_Pp>(__p));}
1165
1166#endif  // _LIBCPP_CXX03_LANG
1167
1168    _LIBCPP_INLINE_VISIBILITY
1169    pair<iterator, bool>
1170        insert(const value_type& __v) {return __tree_.__insert_unique(__v);}
1171
1172    _LIBCPP_INLINE_VISIBILITY
1173    iterator
1174        insert(const_iterator __p, const value_type& __v)
1175            {return __tree_.__insert_unique(__p.__i_, __v);}
1176
1177#ifndef _LIBCPP_CXX03_LANG
1178    _LIBCPP_INLINE_VISIBILITY
1179    pair<iterator, bool>
1180    insert(value_type&& __v) {return __tree_.__insert_unique(_VSTD::move(__v));}
1181
1182    _LIBCPP_INLINE_VISIBILITY
1183    iterator insert(const_iterator __p,  value_type&& __v)
1184    {return __tree_.__insert_unique(__p.__i_, _VSTD::move(__v));}
1185
1186    _LIBCPP_INLINE_VISIBILITY
1187    void insert(initializer_list<value_type> __il)
1188        {insert(__il.begin(), __il.end());}
1189#endif
1190
1191    template <class _InputIterator>
1192        _LIBCPP_INLINE_VISIBILITY
1193        void insert(_InputIterator __f, _InputIterator __l)
1194        {
1195            for (const_iterator __e = cend(); __f != __l; ++__f)
1196                insert(__e.__i_, *__f);
1197        }
1198
1199#if _LIBCPP_STD_VER > 14
1200
1201    template <class... _Args>
1202        _LIBCPP_INLINE_VISIBILITY
1203        pair<iterator, bool> try_emplace(const key_type& __k, _Args&&... __args)
1204    {
1205        return __tree_.__emplace_unique_key_args(__k,
1206            _VSTD::piecewise_construct,
1207            _VSTD::forward_as_tuple(__k),
1208            _VSTD::forward_as_tuple(_VSTD::forward<_Args>(__args)...));
1209    }
1210
1211    template <class... _Args>
1212        _LIBCPP_INLINE_VISIBILITY
1213        pair<iterator, bool> try_emplace(key_type&& __k, _Args&&... __args)
1214    {
1215        return __tree_.__emplace_unique_key_args(__k,
1216            _VSTD::piecewise_construct,
1217            _VSTD::forward_as_tuple(_VSTD::move(__k)),
1218            _VSTD::forward_as_tuple(_VSTD::forward<_Args>(__args)...));
1219    }
1220
1221    template <class... _Args>
1222        _LIBCPP_INLINE_VISIBILITY
1223        iterator try_emplace(const_iterator __h, const key_type& __k, _Args&&... __args)
1224    {
1225        return __tree_.__emplace_hint_unique_key_args(__h.__i_, __k,
1226            _VSTD::piecewise_construct,
1227            _VSTD::forward_as_tuple(__k),
1228            _VSTD::forward_as_tuple(_VSTD::forward<_Args>(__args)...));
1229    }
1230
1231    template <class... _Args>
1232        _LIBCPP_INLINE_VISIBILITY
1233        iterator try_emplace(const_iterator __h, key_type&& __k, _Args&&... __args)
1234    {
1235        return __tree_.__emplace_hint_unique_key_args(__h.__i_, __k,
1236            _VSTD::piecewise_construct,
1237            _VSTD::forward_as_tuple(_VSTD::move(__k)),
1238            _VSTD::forward_as_tuple(_VSTD::forward<_Args>(__args)...));
1239    }
1240
1241    template <class _Vp>
1242        _LIBCPP_INLINE_VISIBILITY
1243        pair<iterator, bool> insert_or_assign(const key_type& __k, _Vp&& __v)
1244    {
1245        iterator __p = lower_bound(__k);
1246        if ( __p != end() && !key_comp()(__k, __p->first))
1247        {
1248            __p->second = _VSTD::forward<_Vp>(__v);
1249            return _VSTD::make_pair(__p, false);
1250        }
1251        return _VSTD::make_pair(emplace_hint(__p, __k, _VSTD::forward<_Vp>(__v)), true);
1252    }
1253
1254    template <class _Vp>
1255        _LIBCPP_INLINE_VISIBILITY
1256        pair<iterator, bool> insert_or_assign(key_type&& __k, _Vp&& __v)
1257    {
1258        iterator __p = lower_bound(__k);
1259        if ( __p != end() && !key_comp()(__k, __p->first))
1260        {
1261            __p->second = _VSTD::forward<_Vp>(__v);
1262            return _VSTD::make_pair(__p, false);
1263        }
1264        return _VSTD::make_pair(emplace_hint(__p, _VSTD::move(__k), _VSTD::forward<_Vp>(__v)), true);
1265    }
1266
1267    template <class _Vp>
1268        _LIBCPP_INLINE_VISIBILITY
1269        iterator insert_or_assign(const_iterator __h, const key_type& __k, _Vp&& __v)
1270     {
1271        iterator __p = lower_bound(__k);
1272        if ( __p != end() && !key_comp()(__k, __p->first))
1273        {
1274            __p->second = _VSTD::forward<_Vp>(__v);
1275            return __p;
1276        }
1277        return emplace_hint(__h, __k, _VSTD::forward<_Vp>(__v));
1278     }
1279
1280    template <class _Vp>
1281        _LIBCPP_INLINE_VISIBILITY
1282        iterator insert_or_assign(const_iterator __h, key_type&& __k, _Vp&& __v)
1283     {
1284        iterator __p = lower_bound(__k);
1285        if ( __p != end() && !key_comp()(__k, __p->first))
1286        {
1287            __p->second = _VSTD::forward<_Vp>(__v);
1288            return __p;
1289        }
1290        return emplace_hint(__h, _VSTD::move(__k), _VSTD::forward<_Vp>(__v));
1291     }
1292
1293#endif // _LIBCPP_STD_VER > 14
1294
1295    _LIBCPP_INLINE_VISIBILITY
1296    iterator erase(const_iterator __p) {return __tree_.erase(__p.__i_);}
1297    _LIBCPP_INLINE_VISIBILITY
1298    iterator erase(iterator __p)       {return __tree_.erase(__p.__i_);}
1299    _LIBCPP_INLINE_VISIBILITY
1300    size_type erase(const key_type& __k)
1301        {return __tree_.__erase_unique(__k);}
1302    _LIBCPP_INLINE_VISIBILITY
1303    iterator  erase(const_iterator __f, const_iterator __l)
1304        {return __tree_.erase(__f.__i_, __l.__i_);}
1305    _LIBCPP_INLINE_VISIBILITY
1306    void clear() _NOEXCEPT {__tree_.clear();}
1307
1308#if _LIBCPP_STD_VER > 14
1309    _LIBCPP_INLINE_VISIBILITY
1310    insert_return_type insert(node_type&& __nh)
1311    {
1312        _LIBCPP_ASSERT(__nh.empty() || __nh.get_allocator() == get_allocator(),
1313            "node_type with incompatible allocator passed to map::insert()");
1314        return __tree_.template __node_handle_insert_unique<
1315            node_type, insert_return_type>(_VSTD::move(__nh));
1316    }
1317    _LIBCPP_INLINE_VISIBILITY
1318    iterator insert(const_iterator __hint, node_type&& __nh)
1319    {
1320        _LIBCPP_ASSERT(__nh.empty() || __nh.get_allocator() == get_allocator(),
1321            "node_type with incompatible allocator passed to map::insert()");
1322        return __tree_.template __node_handle_insert_unique<node_type>(
1323            __hint.__i_, _VSTD::move(__nh));
1324    }
1325    _LIBCPP_INLINE_VISIBILITY
1326    node_type extract(key_type const& __key)
1327    {
1328        return __tree_.template __node_handle_extract<node_type>(__key);
1329    }
1330    _LIBCPP_INLINE_VISIBILITY
1331    node_type extract(const_iterator __it)
1332    {
1333        return __tree_.template __node_handle_extract<node_type>(__it.__i_);
1334    }
1335    template <class _Compare2>
1336    _LIBCPP_INLINE_VISIBILITY
1337    void merge(map<key_type, mapped_type, _Compare2, allocator_type>& __source)
1338    {
1339        _LIBCPP_ASSERT(__source.get_allocator() == get_allocator(),
1340                       "merging container with incompatible allocator");
1341        __tree_.__node_handle_merge_unique(__source.__tree_);
1342    }
1343    template <class _Compare2>
1344    _LIBCPP_INLINE_VISIBILITY
1345    void merge(map<key_type, mapped_type, _Compare2, allocator_type>&& __source)
1346    {
1347        _LIBCPP_ASSERT(__source.get_allocator() == get_allocator(),
1348                       "merging container with incompatible allocator");
1349        __tree_.__node_handle_merge_unique(__source.__tree_);
1350    }
1351    template <class _Compare2>
1352    _LIBCPP_INLINE_VISIBILITY
1353    void merge(multimap<key_type, mapped_type, _Compare2, allocator_type>& __source)
1354    {
1355        _LIBCPP_ASSERT(__source.get_allocator() == get_allocator(),
1356                       "merging container with incompatible allocator");
1357        __tree_.__node_handle_merge_unique(__source.__tree_);
1358    }
1359    template <class _Compare2>
1360    _LIBCPP_INLINE_VISIBILITY
1361    void merge(multimap<key_type, mapped_type, _Compare2, allocator_type>&& __source)
1362    {
1363        _LIBCPP_ASSERT(__source.get_allocator() == get_allocator(),
1364                       "merging container with incompatible allocator");
1365        __tree_.__node_handle_merge_unique(__source.__tree_);
1366    }
1367#endif
1368
1369    _LIBCPP_INLINE_VISIBILITY
1370    void swap(map& __m)
1371        _NOEXCEPT_(__is_nothrow_swappable<__base>::value)
1372        {__tree_.swap(__m.__tree_);}
1373
1374    _LIBCPP_INLINE_VISIBILITY
1375    iterator find(const key_type& __k)             {return __tree_.find(__k);}
1376    _LIBCPP_INLINE_VISIBILITY
1377    const_iterator find(const key_type& __k) const {return __tree_.find(__k);}
1378#if _LIBCPP_STD_VER > 11
1379    template <typename _K2>
1380    _LIBCPP_INLINE_VISIBILITY
1381    typename enable_if<__is_transparent<_Compare, _K2>::value,iterator>::type
1382    find(const _K2& __k)                           {return __tree_.find(__k);}
1383    template <typename _K2>
1384    _LIBCPP_INLINE_VISIBILITY
1385    typename enable_if<__is_transparent<_Compare, _K2>::value,const_iterator>::type
1386    find(const _K2& __k) const                     {return __tree_.find(__k);}
1387#endif
1388
1389    _LIBCPP_INLINE_VISIBILITY
1390    size_type      count(const key_type& __k) const
1391        {return __tree_.__count_unique(__k);}
1392#if _LIBCPP_STD_VER > 11
1393    template <typename _K2>
1394    _LIBCPP_INLINE_VISIBILITY
1395    typename enable_if<__is_transparent<_Compare, _K2>::value,size_type>::type
1396    count(const _K2& __k) const {return __tree_.__count_multi(__k);}
1397#endif
1398    _LIBCPP_INLINE_VISIBILITY
1399    iterator lower_bound(const key_type& __k)
1400        {return __tree_.lower_bound(__k);}
1401    _LIBCPP_INLINE_VISIBILITY
1402    const_iterator lower_bound(const key_type& __k) const
1403        {return __tree_.lower_bound(__k);}
1404#if _LIBCPP_STD_VER > 11
1405    template <typename _K2>
1406    _LIBCPP_INLINE_VISIBILITY
1407    typename enable_if<__is_transparent<_Compare, _K2>::value,iterator>::type
1408    lower_bound(const _K2& __k)       {return __tree_.lower_bound(__k);}
1409
1410    template <typename _K2>
1411    _LIBCPP_INLINE_VISIBILITY
1412    typename enable_if<__is_transparent<_Compare, _K2>::value,const_iterator>::type
1413    lower_bound(const _K2& __k) const {return __tree_.lower_bound(__k);}
1414#endif
1415
1416    _LIBCPP_INLINE_VISIBILITY
1417    iterator upper_bound(const key_type& __k)
1418        {return __tree_.upper_bound(__k);}
1419    _LIBCPP_INLINE_VISIBILITY
1420    const_iterator upper_bound(const key_type& __k) const
1421        {return __tree_.upper_bound(__k);}
1422#if _LIBCPP_STD_VER > 11
1423    template <typename _K2>
1424    _LIBCPP_INLINE_VISIBILITY
1425    typename enable_if<__is_transparent<_Compare, _K2>::value,iterator>::type
1426    upper_bound(const _K2& __k)       {return __tree_.upper_bound(__k);}
1427    template <typename _K2>
1428    _LIBCPP_INLINE_VISIBILITY
1429    typename enable_if<__is_transparent<_Compare, _K2>::value,const_iterator>::type
1430    upper_bound(const _K2& __k) const {return __tree_.upper_bound(__k);}
1431#endif
1432
1433    _LIBCPP_INLINE_VISIBILITY
1434    pair<iterator,iterator> equal_range(const key_type& __k)
1435        {return __tree_.__equal_range_unique(__k);}
1436    _LIBCPP_INLINE_VISIBILITY
1437    pair<const_iterator,const_iterator> equal_range(const key_type& __k) const
1438        {return __tree_.__equal_range_unique(__k);}
1439#if _LIBCPP_STD_VER > 11
1440    template <typename _K2>
1441    _LIBCPP_INLINE_VISIBILITY
1442    typename enable_if<__is_transparent<_Compare, _K2>::value,pair<iterator,iterator>>::type
1443    equal_range(const _K2& __k)       {return __tree_.__equal_range_multi(__k);}
1444    template <typename _K2>
1445    _LIBCPP_INLINE_VISIBILITY
1446    typename enable_if<__is_transparent<_Compare, _K2>::value,pair<const_iterator,const_iterator>>::type
1447    equal_range(const _K2& __k) const {return __tree_.__equal_range_multi(__k);}
1448#endif
1449
1450private:
1451    typedef typename __base::__node                    __node;
1452    typedef typename __base::__node_allocator          __node_allocator;
1453    typedef typename __base::__node_pointer            __node_pointer;
1454    typedef typename __base::__node_base_pointer       __node_base_pointer;
1455    typedef typename __base::__parent_pointer          __parent_pointer;
1456
1457    typedef __map_node_destructor<__node_allocator> _Dp;
1458    typedef unique_ptr<__node, _Dp> __node_holder;
1459
1460#ifdef _LIBCPP_CXX03_LANG
1461    __node_holder __construct_node_with_key(const key_type& __k);
1462#endif
1463};
1464
1465
1466#ifndef _LIBCPP_CXX03_LANG
1467template <class _Key, class _Tp, class _Compare, class _Allocator>
1468map<_Key, _Tp, _Compare, _Allocator>::map(map&& __m, const allocator_type& __a)
1469    : __tree_(_VSTD::move(__m.__tree_), typename __base::allocator_type(__a))
1470{
1471    if (__a != __m.get_allocator())
1472    {
1473        const_iterator __e = cend();
1474        while (!__m.empty())
1475            __tree_.__insert_unique(__e.__i_,
1476                    __m.__tree_.remove(__m.begin().__i_)->__value_.__move());
1477    }
1478}
1479
1480template <class _Key, class _Tp, class _Compare, class _Allocator>
1481_Tp&
1482map<_Key, _Tp, _Compare, _Allocator>::operator[](const key_type& __k)
1483{
1484    return __tree_.__emplace_unique_key_args(__k,
1485        _VSTD::piecewise_construct,
1486        _VSTD::forward_as_tuple(__k),
1487        _VSTD::forward_as_tuple()).first->__get_value().second;
1488}
1489
1490template <class _Key, class _Tp, class _Compare, class _Allocator>
1491_Tp&
1492map<_Key, _Tp, _Compare, _Allocator>::operator[](key_type&& __k)
1493{
1494    return __tree_.__emplace_unique_key_args(__k,
1495        _VSTD::piecewise_construct,
1496        _VSTD::forward_as_tuple(_VSTD::move(__k)),
1497        _VSTD::forward_as_tuple()).first->__get_value().second;
1498}
1499
1500#else // _LIBCPP_CXX03_LANG
1501
1502template <class _Key, class _Tp, class _Compare, class _Allocator>
1503typename map<_Key, _Tp, _Compare, _Allocator>::__node_holder
1504map<_Key, _Tp, _Compare, _Allocator>::__construct_node_with_key(const key_type& __k)
1505{
1506    __node_allocator& __na = __tree_.__node_alloc();
1507    __node_holder __h(__node_traits::allocate(__na, 1), _Dp(__na));
1508    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.__get_value().first), __k);
1509    __h.get_deleter().__first_constructed = true;
1510    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.__get_value().second));
1511    __h.get_deleter().__second_constructed = true;
1512    return _LIBCPP_EXPLICIT_MOVE(__h);  // explicitly moved for C++03
1513}
1514
1515template <class _Key, class _Tp, class _Compare, class _Allocator>
1516_Tp&
1517map<_Key, _Tp, _Compare, _Allocator>::operator[](const key_type& __k)
1518{
1519    __parent_pointer __parent;
1520    __node_base_pointer& __child = __tree_.__find_equal(__parent, __k);
1521    __node_pointer __r = static_cast<__node_pointer>(__child);
1522    if (__child == nullptr)
1523    {
1524        __node_holder __h = __construct_node_with_key(__k);
1525        __tree_.__insert_node_at(__parent, __child, static_cast<__node_base_pointer>(__h.get()));
1526        __r = __h.release();
1527    }
1528    return __r->__value_.__get_value().second;
1529}
1530
1531#endif  // _LIBCPP_CXX03_LANG
1532
1533template <class _Key, class _Tp, class _Compare, class _Allocator>
1534_Tp&
1535map<_Key, _Tp, _Compare, _Allocator>::at(const key_type& __k)
1536{
1537    __parent_pointer __parent;
1538    __node_base_pointer& __child = __tree_.__find_equal(__parent, __k);
1539#ifndef _LIBCPP_NO_EXCEPTIONS
1540    if (__child == nullptr)
1541        throw out_of_range("map::at:  key not found");
1542#endif  // _LIBCPP_NO_EXCEPTIONS
1543    return static_cast<__node_pointer>(__child)->__value_.__get_value().second;
1544}
1545
1546template <class _Key, class _Tp, class _Compare, class _Allocator>
1547const _Tp&
1548map<_Key, _Tp, _Compare, _Allocator>::at(const key_type& __k) const
1549{
1550    __parent_pointer __parent;
1551    __node_base_pointer __child = __tree_.__find_equal(__parent, __k);
1552#ifndef _LIBCPP_NO_EXCEPTIONS
1553    if (__child == nullptr)
1554        throw out_of_range("map::at:  key not found");
1555#endif  // _LIBCPP_NO_EXCEPTIONS
1556    return static_cast<__node_pointer>(__child)->__value_.__get_value().second;
1557}
1558
1559
1560template <class _Key, class _Tp, class _Compare, class _Allocator>
1561inline _LIBCPP_INLINE_VISIBILITY
1562bool
1563operator==(const map<_Key, _Tp, _Compare, _Allocator>& __x,
1564           const map<_Key, _Tp, _Compare, _Allocator>& __y)
1565{
1566    return __x.size() == __y.size() && _VSTD::equal(__x.begin(), __x.end(), __y.begin());
1567}
1568
1569template <class _Key, class _Tp, class _Compare, class _Allocator>
1570inline _LIBCPP_INLINE_VISIBILITY
1571bool
1572operator< (const map<_Key, _Tp, _Compare, _Allocator>& __x,
1573           const map<_Key, _Tp, _Compare, _Allocator>& __y)
1574{
1575    return _VSTD::lexicographical_compare(__x.begin(), __x.end(), __y.begin(), __y.end());
1576}
1577
1578template <class _Key, class _Tp, class _Compare, class _Allocator>
1579inline _LIBCPP_INLINE_VISIBILITY
1580bool
1581operator!=(const map<_Key, _Tp, _Compare, _Allocator>& __x,
1582           const map<_Key, _Tp, _Compare, _Allocator>& __y)
1583{
1584    return !(__x == __y);
1585}
1586
1587template <class _Key, class _Tp, class _Compare, class _Allocator>
1588inline _LIBCPP_INLINE_VISIBILITY
1589bool
1590operator> (const map<_Key, _Tp, _Compare, _Allocator>& __x,
1591           const map<_Key, _Tp, _Compare, _Allocator>& __y)
1592{
1593    return __y < __x;
1594}
1595
1596template <class _Key, class _Tp, class _Compare, class _Allocator>
1597inline _LIBCPP_INLINE_VISIBILITY
1598bool
1599operator>=(const map<_Key, _Tp, _Compare, _Allocator>& __x,
1600           const map<_Key, _Tp, _Compare, _Allocator>& __y)
1601{
1602    return !(__x < __y);
1603}
1604
1605template <class _Key, class _Tp, class _Compare, class _Allocator>
1606inline _LIBCPP_INLINE_VISIBILITY
1607bool
1608operator<=(const map<_Key, _Tp, _Compare, _Allocator>& __x,
1609           const map<_Key, _Tp, _Compare, _Allocator>& __y)
1610{
1611    return !(__y < __x);
1612}
1613
1614template <class _Key, class _Tp, class _Compare, class _Allocator>
1615inline _LIBCPP_INLINE_VISIBILITY
1616void
1617swap(map<_Key, _Tp, _Compare, _Allocator>& __x,
1618     map<_Key, _Tp, _Compare, _Allocator>& __y)
1619    _NOEXCEPT_(_NOEXCEPT_(__x.swap(__y)))
1620{
1621    __x.swap(__y);
1622}
1623
1624#if _LIBCPP_STD_VER > 17
1625template <class _Key, class _Tp, class _Compare, class _Allocator, class _Predicate>
1626inline _LIBCPP_INLINE_VISIBILITY
1627void erase_if(map<_Key, _Tp, _Compare, _Allocator>& __c, _Predicate __pred)
1628{ __libcpp_erase_if_container(__c, __pred); }
1629#endif
1630
1631
1632template <class _Key, class _Tp, class _Compare = less<_Key>,
1633          class _Allocator = allocator<pair<const _Key, _Tp> > >
1634class _LIBCPP_TEMPLATE_VIS multimap
1635{
1636public:
1637    // types:
1638    typedef _Key                                     key_type;
1639    typedef _Tp                                      mapped_type;
1640    typedef pair<const key_type, mapped_type>        value_type;
1641    typedef _Compare                                 key_compare;
1642    typedef _Allocator                               allocator_type;
1643    typedef value_type&                              reference;
1644    typedef const value_type&                        const_reference;
1645
1646    static_assert(sizeof(__diagnose_non_const_comparator<_Key, _Compare>()), "");
1647    static_assert((is_same<typename allocator_type::value_type, value_type>::value),
1648                  "Allocator::value_type must be same type as value_type");
1649
1650    class _LIBCPP_TEMPLATE_VIS value_compare
1651        : public binary_function<value_type, value_type, bool>
1652    {
1653        friend class multimap;
1654    protected:
1655        key_compare comp;
1656
1657        _LIBCPP_INLINE_VISIBILITY
1658        value_compare(key_compare c) : comp(c) {}
1659    public:
1660        _LIBCPP_INLINE_VISIBILITY
1661        bool operator()(const value_type& __x, const value_type& __y) const
1662            {return comp(__x.first, __y.first);}
1663    };
1664
1665private:
1666
1667    typedef _VSTD::__value_type<key_type, mapped_type>             __value_type;
1668    typedef __map_value_compare<key_type, __value_type, key_compare> __vc;
1669    typedef typename __rebind_alloc_helper<allocator_traits<allocator_type>,
1670                                                 __value_type>::type __allocator_type;
1671    typedef __tree<__value_type, __vc, __allocator_type>            __base;
1672    typedef typename __base::__node_traits                          __node_traits;
1673    typedef allocator_traits<allocator_type>                        __alloc_traits;
1674
1675    __base __tree_;
1676
1677public:
1678    typedef typename __alloc_traits::pointer               pointer;
1679    typedef typename __alloc_traits::const_pointer         const_pointer;
1680    typedef typename __alloc_traits::size_type             size_type;
1681    typedef typename __alloc_traits::difference_type       difference_type;
1682    typedef __map_iterator<typename __base::iterator>      iterator;
1683    typedef __map_const_iterator<typename __base::const_iterator> const_iterator;
1684    typedef _VSTD::reverse_iterator<iterator>               reverse_iterator;
1685    typedef _VSTD::reverse_iterator<const_iterator>         const_reverse_iterator;
1686
1687#if _LIBCPP_STD_VER > 14
1688    typedef __map_node_handle<typename __base::__node, allocator_type> node_type;
1689#endif
1690
1691    template <class _Key2, class _Value2, class _Comp2, class _Alloc2>
1692        friend class _LIBCPP_TEMPLATE_VIS map;
1693    template <class _Key2, class _Value2, class _Comp2, class _Alloc2>
1694        friend class _LIBCPP_TEMPLATE_VIS multimap;
1695
1696    _LIBCPP_INLINE_VISIBILITY
1697    multimap()
1698        _NOEXCEPT_(
1699            is_nothrow_default_constructible<allocator_type>::value &&
1700            is_nothrow_default_constructible<key_compare>::value &&
1701            is_nothrow_copy_constructible<key_compare>::value)
1702        : __tree_(__vc(key_compare())) {}
1703
1704    _LIBCPP_INLINE_VISIBILITY
1705    explicit multimap(const key_compare& __comp)
1706        _NOEXCEPT_(
1707            is_nothrow_default_constructible<allocator_type>::value &&
1708            is_nothrow_copy_constructible<key_compare>::value)
1709        : __tree_(__vc(__comp)) {}
1710
1711    _LIBCPP_INLINE_VISIBILITY
1712    explicit multimap(const key_compare& __comp, const allocator_type& __a)
1713        : __tree_(__vc(__comp), typename __base::allocator_type(__a)) {}
1714
1715    template <class _InputIterator>
1716        _LIBCPP_INLINE_VISIBILITY
1717        multimap(_InputIterator __f, _InputIterator __l,
1718            const key_compare& __comp = key_compare())
1719        : __tree_(__vc(__comp))
1720        {
1721            insert(__f, __l);
1722        }
1723
1724    template <class _InputIterator>
1725        _LIBCPP_INLINE_VISIBILITY
1726        multimap(_InputIterator __f, _InputIterator __l,
1727            const key_compare& __comp, const allocator_type& __a)
1728        : __tree_(__vc(__comp), typename __base::allocator_type(__a))
1729        {
1730            insert(__f, __l);
1731        }
1732
1733#if _LIBCPP_STD_VER > 11
1734    template <class _InputIterator>
1735    _LIBCPP_INLINE_VISIBILITY
1736    multimap(_InputIterator __f, _InputIterator __l, const allocator_type& __a)
1737        : multimap(__f, __l, key_compare(), __a) {}
1738#endif
1739
1740    _LIBCPP_INLINE_VISIBILITY
1741    multimap(const multimap& __m)
1742        : __tree_(__m.__tree_.value_comp(),
1743          __alloc_traits::select_on_container_copy_construction(__m.__tree_.__alloc()))
1744        {
1745            insert(__m.begin(), __m.end());
1746        }
1747
1748    _LIBCPP_INLINE_VISIBILITY
1749    multimap& operator=(const multimap& __m)
1750        {
1751#ifndef _LIBCPP_CXX03_LANG
1752            __tree_ = __m.__tree_;
1753#else
1754            if (this != &__m) {
1755                __tree_.clear();
1756                __tree_.value_comp() = __m.__tree_.value_comp();
1757                __tree_.__copy_assign_alloc(__m.__tree_);
1758                insert(__m.begin(), __m.end());
1759            }
1760#endif
1761            return *this;
1762        }
1763
1764#ifndef _LIBCPP_CXX03_LANG
1765
1766    _LIBCPP_INLINE_VISIBILITY
1767    multimap(multimap&& __m)
1768        _NOEXCEPT_(is_nothrow_move_constructible<__base>::value)
1769        : __tree_(_VSTD::move(__m.__tree_))
1770        {
1771        }
1772
1773    multimap(multimap&& __m, const allocator_type& __a);
1774
1775    _LIBCPP_INLINE_VISIBILITY
1776    multimap& operator=(multimap&& __m)
1777        _NOEXCEPT_(is_nothrow_move_assignable<__base>::value)
1778        {
1779            __tree_ = _VSTD::move(__m.__tree_);
1780            return *this;
1781        }
1782
1783    _LIBCPP_INLINE_VISIBILITY
1784    multimap(initializer_list<value_type> __il, const key_compare& __comp = key_compare())
1785        : __tree_(__vc(__comp))
1786        {
1787            insert(__il.begin(), __il.end());
1788        }
1789
1790    _LIBCPP_INLINE_VISIBILITY
1791    multimap(initializer_list<value_type> __il, const key_compare& __comp, const allocator_type& __a)
1792        : __tree_(__vc(__comp), typename __base::allocator_type(__a))
1793        {
1794            insert(__il.begin(), __il.end());
1795        }
1796
1797#if _LIBCPP_STD_VER > 11
1798    _LIBCPP_INLINE_VISIBILITY
1799    multimap(initializer_list<value_type> __il, const allocator_type& __a)
1800        : multimap(__il, key_compare(), __a) {}
1801#endif
1802
1803    _LIBCPP_INLINE_VISIBILITY
1804    multimap& operator=(initializer_list<value_type> __il)
1805        {
1806            __tree_.__assign_multi(__il.begin(), __il.end());
1807            return *this;
1808        }
1809
1810#endif  // _LIBCPP_CXX03_LANG
1811
1812    _LIBCPP_INLINE_VISIBILITY
1813    explicit multimap(const allocator_type& __a)
1814        : __tree_(typename __base::allocator_type(__a))
1815        {
1816        }
1817
1818    _LIBCPP_INLINE_VISIBILITY
1819    multimap(const multimap& __m, const allocator_type& __a)
1820        : __tree_(__m.__tree_.value_comp(), typename __base::allocator_type(__a))
1821        {
1822            insert(__m.begin(), __m.end());
1823        }
1824
1825    _LIBCPP_INLINE_VISIBILITY
1826          iterator begin() _NOEXCEPT {return __tree_.begin();}
1827    _LIBCPP_INLINE_VISIBILITY
1828    const_iterator begin() const _NOEXCEPT {return __tree_.begin();}
1829    _LIBCPP_INLINE_VISIBILITY
1830          iterator end() _NOEXCEPT {return __tree_.end();}
1831    _LIBCPP_INLINE_VISIBILITY
1832    const_iterator end() const _NOEXCEPT {return __tree_.end();}
1833
1834    _LIBCPP_INLINE_VISIBILITY
1835          reverse_iterator rbegin() _NOEXCEPT {return reverse_iterator(end());}
1836    _LIBCPP_INLINE_VISIBILITY
1837    const_reverse_iterator rbegin() const _NOEXCEPT
1838        {return const_reverse_iterator(end());}
1839    _LIBCPP_INLINE_VISIBILITY
1840          reverse_iterator rend() _NOEXCEPT {return reverse_iterator(begin());}
1841    _LIBCPP_INLINE_VISIBILITY
1842    const_reverse_iterator rend() const _NOEXCEPT
1843        {return const_reverse_iterator(begin());}
1844
1845    _LIBCPP_INLINE_VISIBILITY
1846    const_iterator cbegin()  const _NOEXCEPT {return begin();}
1847    _LIBCPP_INLINE_VISIBILITY
1848    const_iterator cend() const _NOEXCEPT {return end();}
1849    _LIBCPP_INLINE_VISIBILITY
1850    const_reverse_iterator crbegin() const _NOEXCEPT {return rbegin();}
1851    _LIBCPP_INLINE_VISIBILITY
1852    const_reverse_iterator crend() const _NOEXCEPT {return rend();}
1853
1854    _LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_INLINE_VISIBILITY
1855    bool empty() const _NOEXCEPT {return __tree_.size() == 0;}
1856    _LIBCPP_INLINE_VISIBILITY
1857    size_type size() const _NOEXCEPT {return __tree_.size();}
1858    _LIBCPP_INLINE_VISIBILITY
1859    size_type max_size() const _NOEXCEPT {return __tree_.max_size();}
1860
1861    _LIBCPP_INLINE_VISIBILITY
1862    allocator_type get_allocator() const _NOEXCEPT {return allocator_type(__tree_.__alloc());}
1863    _LIBCPP_INLINE_VISIBILITY
1864    key_compare    key_comp() const {return __tree_.value_comp().key_comp();}
1865    _LIBCPP_INLINE_VISIBILITY
1866    value_compare  value_comp() const
1867        {return value_compare(__tree_.value_comp().key_comp());}
1868
1869#ifndef _LIBCPP_CXX03_LANG
1870
1871    template <class ..._Args>
1872    _LIBCPP_INLINE_VISIBILITY
1873    iterator emplace(_Args&& ...__args) {
1874        return __tree_.__emplace_multi(_VSTD::forward<_Args>(__args)...);
1875    }
1876
1877    template <class ..._Args>
1878    _LIBCPP_INLINE_VISIBILITY
1879    iterator emplace_hint(const_iterator __p, _Args&& ...__args) {
1880        return __tree_.__emplace_hint_multi(__p.__i_, _VSTD::forward<_Args>(__args)...);
1881    }
1882
1883    template <class _Pp,
1884              class = typename enable_if<is_constructible<value_type, _Pp>::value>::type>
1885        _LIBCPP_INLINE_VISIBILITY
1886        iterator insert(_Pp&& __p)
1887            {return __tree_.__insert_multi(_VSTD::forward<_Pp>(__p));}
1888
1889    template <class _Pp,
1890              class = typename enable_if<is_constructible<value_type, _Pp>::value>::type>
1891        _LIBCPP_INLINE_VISIBILITY
1892        iterator insert(const_iterator __pos, _Pp&& __p)
1893            {return __tree_.__insert_multi(__pos.__i_, _VSTD::forward<_Pp>(__p));}
1894
1895    _LIBCPP_INLINE_VISIBILITY
1896    iterator insert(value_type&& __v)
1897        {return __tree_.__insert_multi(_VSTD::move(__v));}
1898
1899    _LIBCPP_INLINE_VISIBILITY
1900    iterator insert(const_iterator __p, value_type&& __v)
1901        {return __tree_.__insert_multi(__p.__i_, _VSTD::move(__v));}
1902
1903
1904    _LIBCPP_INLINE_VISIBILITY
1905    void insert(initializer_list<value_type> __il)
1906        {insert(__il.begin(), __il.end());}
1907
1908#endif  // _LIBCPP_CXX03_LANG
1909
1910    _LIBCPP_INLINE_VISIBILITY
1911    iterator insert(const value_type& __v) {return __tree_.__insert_multi(__v);}
1912
1913    _LIBCPP_INLINE_VISIBILITY
1914    iterator insert(const_iterator __p, const value_type& __v)
1915            {return __tree_.__insert_multi(__p.__i_, __v);}
1916
1917    template <class _InputIterator>
1918        _LIBCPP_INLINE_VISIBILITY
1919        void insert(_InputIterator __f, _InputIterator __l)
1920        {
1921            for (const_iterator __e = cend(); __f != __l; ++__f)
1922                __tree_.__insert_multi(__e.__i_, *__f);
1923        }
1924
1925    _LIBCPP_INLINE_VISIBILITY
1926    iterator erase(const_iterator __p) {return __tree_.erase(__p.__i_);}
1927    _LIBCPP_INLINE_VISIBILITY
1928    iterator erase(iterator __p)       {return __tree_.erase(__p.__i_);}
1929    _LIBCPP_INLINE_VISIBILITY
1930    size_type erase(const key_type& __k) {return __tree_.__erase_multi(__k);}
1931    _LIBCPP_INLINE_VISIBILITY
1932    iterator  erase(const_iterator __f, const_iterator __l)
1933        {return __tree_.erase(__f.__i_, __l.__i_);}
1934
1935#if _LIBCPP_STD_VER > 14
1936    _LIBCPP_INLINE_VISIBILITY
1937    iterator insert(node_type&& __nh)
1938    {
1939        _LIBCPP_ASSERT(__nh.empty() || __nh.get_allocator() == get_allocator(),
1940            "node_type with incompatible allocator passed to multimap::insert()");
1941        return __tree_.template __node_handle_insert_multi<node_type>(
1942            _VSTD::move(__nh));
1943    }
1944    _LIBCPP_INLINE_VISIBILITY
1945    iterator insert(const_iterator __hint, node_type&& __nh)
1946    {
1947        _LIBCPP_ASSERT(__nh.empty() || __nh.get_allocator() == get_allocator(),
1948            "node_type with incompatible allocator passed to multimap::insert()");
1949        return __tree_.template __node_handle_insert_multi<node_type>(
1950            __hint.__i_, _VSTD::move(__nh));
1951    }
1952    _LIBCPP_INLINE_VISIBILITY
1953    node_type extract(key_type const& __key)
1954    {
1955        return __tree_.template __node_handle_extract<node_type>(__key);
1956    }
1957    _LIBCPP_INLINE_VISIBILITY
1958    node_type extract(const_iterator __it)
1959    {
1960        return __tree_.template __node_handle_extract<node_type>(
1961            __it.__i_);
1962    }
1963    template <class _Compare2>
1964    _LIBCPP_INLINE_VISIBILITY
1965    void merge(multimap<key_type, mapped_type, _Compare2, allocator_type>& __source)
1966    {
1967        _LIBCPP_ASSERT(__source.get_allocator() == get_allocator(),
1968                       "merging container with incompatible allocator");
1969        return __tree_.__node_handle_merge_multi(__source.__tree_);
1970    }
1971    template <class _Compare2>
1972    _LIBCPP_INLINE_VISIBILITY
1973    void merge(multimap<key_type, mapped_type, _Compare2, allocator_type>&& __source)
1974    {
1975        _LIBCPP_ASSERT(__source.get_allocator() == get_allocator(),
1976                       "merging container with incompatible allocator");
1977        return __tree_.__node_handle_merge_multi(__source.__tree_);
1978    }
1979    template <class _Compare2>
1980    _LIBCPP_INLINE_VISIBILITY
1981    void merge(map<key_type, mapped_type, _Compare2, allocator_type>& __source)
1982    {
1983        _LIBCPP_ASSERT(__source.get_allocator() == get_allocator(),
1984                       "merging container with incompatible allocator");
1985        return __tree_.__node_handle_merge_multi(__source.__tree_);
1986    }
1987    template <class _Compare2>
1988    _LIBCPP_INLINE_VISIBILITY
1989    void merge(map<key_type, mapped_type, _Compare2, allocator_type>&& __source)
1990    {
1991        _LIBCPP_ASSERT(__source.get_allocator() == get_allocator(),
1992                       "merging container with incompatible allocator");
1993        return __tree_.__node_handle_merge_multi(__source.__tree_);
1994    }
1995#endif
1996
1997    _LIBCPP_INLINE_VISIBILITY
1998    void clear() _NOEXCEPT {__tree_.clear();}
1999
2000    _LIBCPP_INLINE_VISIBILITY
2001    void swap(multimap& __m)
2002        _NOEXCEPT_(__is_nothrow_swappable<__base>::value)
2003        {__tree_.swap(__m.__tree_);}
2004
2005    _LIBCPP_INLINE_VISIBILITY
2006    iterator find(const key_type& __k)             {return __tree_.find(__k);}
2007    _LIBCPP_INLINE_VISIBILITY
2008    const_iterator find(const key_type& __k) const {return __tree_.find(__k);}
2009#if _LIBCPP_STD_VER > 11
2010    template <typename _K2>
2011    _LIBCPP_INLINE_VISIBILITY
2012    typename enable_if<__is_transparent<_Compare, _K2>::value,iterator>::type
2013    find(const _K2& __k)                           {return __tree_.find(__k);}
2014    template <typename _K2>
2015    _LIBCPP_INLINE_VISIBILITY
2016    typename enable_if<__is_transparent<_Compare, _K2>::value,const_iterator>::type
2017    find(const _K2& __k) const                     {return __tree_.find(__k);}
2018#endif
2019
2020    _LIBCPP_INLINE_VISIBILITY
2021    size_type      count(const key_type& __k) const
2022        {return __tree_.__count_multi(__k);}
2023#if _LIBCPP_STD_VER > 11
2024    template <typename _K2>
2025    _LIBCPP_INLINE_VISIBILITY
2026    typename enable_if<__is_transparent<_Compare, _K2>::value,size_type>::type
2027    count(const _K2& __k) const {return __tree_.__count_multi(__k);}
2028#endif
2029    _LIBCPP_INLINE_VISIBILITY
2030    iterator lower_bound(const key_type& __k)
2031        {return __tree_.lower_bound(__k);}
2032    _LIBCPP_INLINE_VISIBILITY
2033    const_iterator lower_bound(const key_type& __k) const
2034            {return __tree_.lower_bound(__k);}
2035#if _LIBCPP_STD_VER > 11
2036    template <typename _K2>
2037    _LIBCPP_INLINE_VISIBILITY
2038    typename enable_if<__is_transparent<_Compare, _K2>::value,iterator>::type
2039    lower_bound(const _K2& __k)       {return __tree_.lower_bound(__k);}
2040
2041    template <typename _K2>
2042    _LIBCPP_INLINE_VISIBILITY
2043    typename enable_if<__is_transparent<_Compare, _K2>::value,const_iterator>::type
2044    lower_bound(const _K2& __k) const {return __tree_.lower_bound(__k);}
2045#endif
2046
2047    _LIBCPP_INLINE_VISIBILITY
2048    iterator upper_bound(const key_type& __k)
2049            {return __tree_.upper_bound(__k);}
2050    _LIBCPP_INLINE_VISIBILITY
2051    const_iterator upper_bound(const key_type& __k) const
2052            {return __tree_.upper_bound(__k);}
2053#if _LIBCPP_STD_VER > 11
2054    template <typename _K2>
2055    _LIBCPP_INLINE_VISIBILITY
2056    typename enable_if<__is_transparent<_Compare, _K2>::value,iterator>::type
2057    upper_bound(const _K2& __k)       {return __tree_.upper_bound(__k);}
2058    template <typename _K2>
2059    _LIBCPP_INLINE_VISIBILITY
2060    typename enable_if<__is_transparent<_Compare, _K2>::value,const_iterator>::type
2061    upper_bound(const _K2& __k) const {return __tree_.upper_bound(__k);}
2062#endif
2063
2064    _LIBCPP_INLINE_VISIBILITY
2065    pair<iterator,iterator>             equal_range(const key_type& __k)
2066            {return __tree_.__equal_range_multi(__k);}
2067    _LIBCPP_INLINE_VISIBILITY
2068    pair<const_iterator,const_iterator> equal_range(const key_type& __k) const
2069            {return __tree_.__equal_range_multi(__k);}
2070#if _LIBCPP_STD_VER > 11
2071    template <typename _K2>
2072    _LIBCPP_INLINE_VISIBILITY
2073    typename enable_if<__is_transparent<_Compare, _K2>::value,pair<iterator,iterator>>::type
2074    equal_range(const _K2& __k)       {return __tree_.__equal_range_multi(__k);}
2075    template <typename _K2>
2076    _LIBCPP_INLINE_VISIBILITY
2077    typename enable_if<__is_transparent<_Compare, _K2>::value,pair<const_iterator,const_iterator>>::type
2078    equal_range(const _K2& __k) const {return __tree_.__equal_range_multi(__k);}
2079#endif
2080
2081private:
2082    typedef typename __base::__node                    __node;
2083    typedef typename __base::__node_allocator          __node_allocator;
2084    typedef typename __base::__node_pointer            __node_pointer;
2085
2086    typedef __map_node_destructor<__node_allocator> _Dp;
2087    typedef unique_ptr<__node, _Dp> __node_holder;
2088};
2089
2090#ifndef _LIBCPP_CXX03_LANG
2091template <class _Key, class _Tp, class _Compare, class _Allocator>
2092multimap<_Key, _Tp, _Compare, _Allocator>::multimap(multimap&& __m, const allocator_type& __a)
2093    : __tree_(_VSTD::move(__m.__tree_), typename __base::allocator_type(__a))
2094{
2095    if (__a != __m.get_allocator())
2096    {
2097        const_iterator __e = cend();
2098        while (!__m.empty())
2099            __tree_.__insert_multi(__e.__i_,
2100                    _VSTD::move(__m.__tree_.remove(__m.begin().__i_)->__value_.__move()));
2101    }
2102}
2103#endif
2104
2105template <class _Key, class _Tp, class _Compare, class _Allocator>
2106inline _LIBCPP_INLINE_VISIBILITY
2107bool
2108operator==(const multimap<_Key, _Tp, _Compare, _Allocator>& __x,
2109           const multimap<_Key, _Tp, _Compare, _Allocator>& __y)
2110{
2111    return __x.size() == __y.size() && _VSTD::equal(__x.begin(), __x.end(), __y.begin());
2112}
2113
2114template <class _Key, class _Tp, class _Compare, class _Allocator>
2115inline _LIBCPP_INLINE_VISIBILITY
2116bool
2117operator< (const multimap<_Key, _Tp, _Compare, _Allocator>& __x,
2118           const multimap<_Key, _Tp, _Compare, _Allocator>& __y)
2119{
2120    return _VSTD::lexicographical_compare(__x.begin(), __x.end(), __y.begin(), __y.end());
2121}
2122
2123template <class _Key, class _Tp, class _Compare, class _Allocator>
2124inline _LIBCPP_INLINE_VISIBILITY
2125bool
2126operator!=(const multimap<_Key, _Tp, _Compare, _Allocator>& __x,
2127           const multimap<_Key, _Tp, _Compare, _Allocator>& __y)
2128{
2129    return !(__x == __y);
2130}
2131
2132template <class _Key, class _Tp, class _Compare, class _Allocator>
2133inline _LIBCPP_INLINE_VISIBILITY
2134bool
2135operator> (const multimap<_Key, _Tp, _Compare, _Allocator>& __x,
2136           const multimap<_Key, _Tp, _Compare, _Allocator>& __y)
2137{
2138    return __y < __x;
2139}
2140
2141template <class _Key, class _Tp, class _Compare, class _Allocator>
2142inline _LIBCPP_INLINE_VISIBILITY
2143bool
2144operator>=(const multimap<_Key, _Tp, _Compare, _Allocator>& __x,
2145           const multimap<_Key, _Tp, _Compare, _Allocator>& __y)
2146{
2147    return !(__x < __y);
2148}
2149
2150template <class _Key, class _Tp, class _Compare, class _Allocator>
2151inline _LIBCPP_INLINE_VISIBILITY
2152bool
2153operator<=(const multimap<_Key, _Tp, _Compare, _Allocator>& __x,
2154           const multimap<_Key, _Tp, _Compare, _Allocator>& __y)
2155{
2156    return !(__y < __x);
2157}
2158
2159template <class _Key, class _Tp, class _Compare, class _Allocator>
2160inline _LIBCPP_INLINE_VISIBILITY
2161void
2162swap(multimap<_Key, _Tp, _Compare, _Allocator>& __x,
2163     multimap<_Key, _Tp, _Compare, _Allocator>& __y)
2164    _NOEXCEPT_(_NOEXCEPT_(__x.swap(__y)))
2165{
2166    __x.swap(__y);
2167}
2168
2169#if _LIBCPP_STD_VER > 17
2170template <class _Key, class _Tp, class _Compare, class _Allocator, class _Predicate>
2171inline _LIBCPP_INLINE_VISIBILITY
2172void erase_if(multimap<_Key, _Tp, _Compare, _Allocator>& __c, _Predicate __pred)
2173{ __libcpp_erase_if_container(__c, __pred); }
2174#endif
2175
2176_LIBCPP_END_NAMESPACE_STD
2177
2178#endif  // _LIBCPP_MAP
2179