xref: /freebsd/contrib/llvm-project/libcxx/include/map (revision 5f757f3ff9144b609b3c433dfd370cc6bdc191ad)
10b57cec5SDimitry Andric// -*- C++ -*-
2349cc55cSDimitry Andric//===----------------------------------------------------------------------===//
30b57cec5SDimitry Andric//
40b57cec5SDimitry Andric// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
50b57cec5SDimitry Andric// See https://llvm.org/LICENSE.txt for license information.
60b57cec5SDimitry Andric// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
70b57cec5SDimitry Andric//
80b57cec5SDimitry Andric//===----------------------------------------------------------------------===//
90b57cec5SDimitry Andric
100b57cec5SDimitry Andric#ifndef _LIBCPP_MAP
110b57cec5SDimitry Andric#define _LIBCPP_MAP
120b57cec5SDimitry Andric
130b57cec5SDimitry Andric/*
140b57cec5SDimitry Andric
150b57cec5SDimitry Andric    map synopsis
160b57cec5SDimitry Andric
170b57cec5SDimitry Andricnamespace std
180b57cec5SDimitry Andric{
190b57cec5SDimitry Andric
200b57cec5SDimitry Andrictemplate <class Key, class T, class Compare = less<Key>,
210b57cec5SDimitry Andric          class Allocator = allocator<pair<const Key, T>>>
220b57cec5SDimitry Andricclass map
230b57cec5SDimitry Andric{
240b57cec5SDimitry Andricpublic:
250b57cec5SDimitry Andric    // types:
260b57cec5SDimitry Andric    typedef Key                                      key_type;
270b57cec5SDimitry Andric    typedef T                                        mapped_type;
280b57cec5SDimitry Andric    typedef pair<const key_type, mapped_type>        value_type;
290b57cec5SDimitry Andric    typedef Compare                                  key_compare;
300b57cec5SDimitry Andric    typedef Allocator                                allocator_type;
310b57cec5SDimitry Andric    typedef typename allocator_type::reference       reference;
320b57cec5SDimitry Andric    typedef typename allocator_type::const_reference const_reference;
330b57cec5SDimitry Andric    typedef typename allocator_type::pointer         pointer;
340b57cec5SDimitry Andric    typedef typename allocator_type::const_pointer   const_pointer;
350b57cec5SDimitry Andric    typedef typename allocator_type::size_type       size_type;
360b57cec5SDimitry Andric    typedef typename allocator_type::difference_type difference_type;
370b57cec5SDimitry Andric
380b57cec5SDimitry Andric    typedef implementation-defined                   iterator;
390b57cec5SDimitry Andric    typedef implementation-defined                   const_iterator;
400b57cec5SDimitry Andric    typedef std::reverse_iterator<iterator>          reverse_iterator;
410b57cec5SDimitry Andric    typedef std::reverse_iterator<const_iterator>    const_reverse_iterator;
420b57cec5SDimitry Andric    typedef unspecified                              node_type;              // C++17
430b57cec5SDimitry Andric    typedef INSERT_RETURN_TYPE<iterator, node_type>  insert_return_type;     // C++17
440b57cec5SDimitry Andric
450b57cec5SDimitry Andric    class value_compare
460b57cec5SDimitry Andric    {
470b57cec5SDimitry Andric        friend class map;
480b57cec5SDimitry Andric    protected:
490b57cec5SDimitry Andric        key_compare comp;
500b57cec5SDimitry Andric
510b57cec5SDimitry Andric        value_compare(key_compare c);
520b57cec5SDimitry Andric    public:
53fe6060f1SDimitry Andric        typedef bool result_type;  // deprecated in C++17, removed in C++20
54fe6060f1SDimitry Andric        typedef value_type first_argument_type;  // deprecated in C++17, removed in C++20
55fe6060f1SDimitry Andric        typedef value_type second_argument_type;  // deprecated in C++17, removed in C++20
560b57cec5SDimitry Andric        bool operator()(const value_type& x, const value_type& y) const;
570b57cec5SDimitry Andric    };
580b57cec5SDimitry Andric
590b57cec5SDimitry Andric    // construct/copy/destroy:
600b57cec5SDimitry Andric    map()
610b57cec5SDimitry Andric        noexcept(
620b57cec5SDimitry Andric            is_nothrow_default_constructible<allocator_type>::value &&
630b57cec5SDimitry Andric            is_nothrow_default_constructible<key_compare>::value &&
640b57cec5SDimitry Andric            is_nothrow_copy_constructible<key_compare>::value);
650b57cec5SDimitry Andric    explicit map(const key_compare& comp);
660b57cec5SDimitry Andric    map(const key_compare& comp, const allocator_type& a);
670b57cec5SDimitry Andric    template <class InputIterator>
680b57cec5SDimitry Andric        map(InputIterator first, InputIterator last,
690b57cec5SDimitry Andric            const key_compare& comp = key_compare());
700b57cec5SDimitry Andric    template <class InputIterator>
710b57cec5SDimitry Andric        map(InputIterator first, InputIterator last,
720b57cec5SDimitry Andric            const key_compare& comp, const allocator_type& a);
7306c3fb27SDimitry Andric    template<container-compatible-range<value_type> R>
7406c3fb27SDimitry Andric      map(from_range_t, R&& rg, const Compare& comp = Compare(), const Allocator& = Allocator()); // C++23
750b57cec5SDimitry Andric    map(const map& m);
760b57cec5SDimitry Andric    map(map&& m)
770b57cec5SDimitry Andric        noexcept(
780b57cec5SDimitry Andric            is_nothrow_move_constructible<allocator_type>::value &&
790b57cec5SDimitry Andric            is_nothrow_move_constructible<key_compare>::value);
800b57cec5SDimitry Andric    explicit map(const allocator_type& a);
810b57cec5SDimitry Andric    map(const map& m, const allocator_type& a);
820b57cec5SDimitry Andric    map(map&& m, const allocator_type& a);
830b57cec5SDimitry Andric    map(initializer_list<value_type> il, const key_compare& comp = key_compare());
840b57cec5SDimitry Andric    map(initializer_list<value_type> il, const key_compare& comp, const allocator_type& a);
850b57cec5SDimitry Andric    template <class InputIterator>
860b57cec5SDimitry Andric        map(InputIterator first, InputIterator last, const allocator_type& a)
870b57cec5SDimitry Andric            : map(first, last, Compare(), a) {}  // C++14
8806c3fb27SDimitry Andric    template<container-compatible-range<value_type> R>
8906c3fb27SDimitry Andric      map(from_range_t, R&& rg, const Allocator& a))
9006c3fb27SDimitry Andric        : map(from_range, std::forward<R>(rg), Compare(), a) { } // C++23
910b57cec5SDimitry Andric    map(initializer_list<value_type> il, const allocator_type& a)
920b57cec5SDimitry Andric        : map(il, Compare(), a) {}  // C++14
930b57cec5SDimitry Andric   ~map();
940b57cec5SDimitry Andric
950b57cec5SDimitry Andric    map& operator=(const map& m);
960b57cec5SDimitry Andric    map& operator=(map&& m)
970b57cec5SDimitry Andric        noexcept(
980b57cec5SDimitry Andric            allocator_type::propagate_on_container_move_assignment::value &&
990b57cec5SDimitry Andric            is_nothrow_move_assignable<allocator_type>::value &&
1000b57cec5SDimitry Andric            is_nothrow_move_assignable<key_compare>::value);
1010b57cec5SDimitry Andric    map& operator=(initializer_list<value_type> il);
1020b57cec5SDimitry Andric
1030b57cec5SDimitry Andric    // iterators:
1040b57cec5SDimitry Andric          iterator begin() noexcept;
1050b57cec5SDimitry Andric    const_iterator begin() const noexcept;
1060b57cec5SDimitry Andric          iterator end() noexcept;
1070b57cec5SDimitry Andric    const_iterator end()   const noexcept;
1080b57cec5SDimitry Andric
1090b57cec5SDimitry Andric          reverse_iterator rbegin() noexcept;
1100b57cec5SDimitry Andric    const_reverse_iterator rbegin() const noexcept;
1110b57cec5SDimitry Andric          reverse_iterator rend() noexcept;
1120b57cec5SDimitry Andric    const_reverse_iterator rend()   const noexcept;
1130b57cec5SDimitry Andric
1140b57cec5SDimitry Andric    const_iterator         cbegin()  const noexcept;
1150b57cec5SDimitry Andric    const_iterator         cend()    const noexcept;
1160b57cec5SDimitry Andric    const_reverse_iterator crbegin() const noexcept;
1170b57cec5SDimitry Andric    const_reverse_iterator crend()   const noexcept;
1180b57cec5SDimitry Andric
1190b57cec5SDimitry Andric    // capacity:
1200b57cec5SDimitry Andric    bool      empty()    const noexcept;
1210b57cec5SDimitry Andric    size_type size()     const noexcept;
1220b57cec5SDimitry Andric    size_type max_size() const noexcept;
1230b57cec5SDimitry Andric
1240b57cec5SDimitry Andric    // element access:
1250b57cec5SDimitry Andric    mapped_type& operator[](const key_type& k);
1260b57cec5SDimitry Andric    mapped_type& operator[](key_type&& k);
1270b57cec5SDimitry Andric
1280b57cec5SDimitry Andric          mapped_type& at(const key_type& k);
1290b57cec5SDimitry Andric    const mapped_type& at(const key_type& k) const;
1300b57cec5SDimitry Andric
1310b57cec5SDimitry Andric    // modifiers:
1320b57cec5SDimitry Andric    template <class... Args>
1330b57cec5SDimitry Andric        pair<iterator, bool> emplace(Args&&... args);
1340b57cec5SDimitry Andric    template <class... Args>
1350b57cec5SDimitry Andric        iterator emplace_hint(const_iterator position, Args&&... args);
1360b57cec5SDimitry Andric    pair<iterator, bool> insert(const value_type& v);
1370b57cec5SDimitry Andric    pair<iterator, bool> insert(      value_type&& v);                                // C++17
1380b57cec5SDimitry Andric    template <class P>
1390b57cec5SDimitry Andric        pair<iterator, bool> insert(P&& p);
1400b57cec5SDimitry Andric    iterator insert(const_iterator position, const value_type& v);
1410b57cec5SDimitry Andric    iterator insert(const_iterator position,       value_type&& v);                   // C++17
1420b57cec5SDimitry Andric    template <class P>
1430b57cec5SDimitry Andric        iterator insert(const_iterator position, P&& p);
1440b57cec5SDimitry Andric    template <class InputIterator>
1450b57cec5SDimitry Andric        void insert(InputIterator first, InputIterator last);
14606c3fb27SDimitry Andric    template<container-compatible-range<value_type> R>
14706c3fb27SDimitry Andric      void insert_range(R&& rg);                                                      // C++23
1480b57cec5SDimitry Andric    void insert(initializer_list<value_type> il);
1490b57cec5SDimitry Andric
1500b57cec5SDimitry Andric    node_type extract(const_iterator position);                                       // C++17
1510b57cec5SDimitry Andric    node_type extract(const key_type& x);                                             // C++17
1520b57cec5SDimitry Andric    insert_return_type insert(node_type&& nh);                                        // C++17
1530b57cec5SDimitry Andric    iterator insert(const_iterator hint, node_type&& nh);                             // C++17
1540b57cec5SDimitry Andric
1550b57cec5SDimitry Andric    template <class... Args>
1560b57cec5SDimitry Andric        pair<iterator, bool> try_emplace(const key_type& k, Args&&... args);          // C++17
1570b57cec5SDimitry Andric    template <class... Args>
1580b57cec5SDimitry Andric        pair<iterator, bool> try_emplace(key_type&& k, Args&&... args);               // C++17
1590b57cec5SDimitry Andric    template <class... Args>
1600b57cec5SDimitry Andric        iterator try_emplace(const_iterator hint, const key_type& k, Args&&... args); // C++17
1610b57cec5SDimitry Andric    template <class... Args>
1620b57cec5SDimitry Andric        iterator try_emplace(const_iterator hint, key_type&& k, Args&&... args);      // C++17
1630b57cec5SDimitry Andric    template <class M>
1640b57cec5SDimitry Andric        pair<iterator, bool> insert_or_assign(const key_type& k, M&& obj);            // C++17
1650b57cec5SDimitry Andric    template <class M>
1660b57cec5SDimitry Andric        pair<iterator, bool> insert_or_assign(key_type&& k, M&& obj);                 // C++17
1670b57cec5SDimitry Andric    template <class M>
1680b57cec5SDimitry Andric        iterator insert_or_assign(const_iterator hint, const key_type& k, M&& obj);   // C++17
1690b57cec5SDimitry Andric    template <class M>
1700b57cec5SDimitry Andric        iterator insert_or_assign(const_iterator hint, key_type&& k, M&& obj);        // C++17
1710b57cec5SDimitry Andric
1720b57cec5SDimitry Andric    iterator  erase(const_iterator position);
1730b57cec5SDimitry Andric    iterator  erase(iterator position); // C++14
1740b57cec5SDimitry Andric    size_type erase(const key_type& k);
1750b57cec5SDimitry Andric    iterator  erase(const_iterator first, const_iterator last);
1760b57cec5SDimitry Andric    void clear() noexcept;
1770b57cec5SDimitry Andric
1780b57cec5SDimitry Andric    template<class C2>
1790b57cec5SDimitry Andric      void merge(map<Key, T, C2, Allocator>& source);         // C++17
1800b57cec5SDimitry Andric    template<class C2>
1810b57cec5SDimitry Andric      void merge(map<Key, T, C2, Allocator>&& source);        // C++17
1820b57cec5SDimitry Andric    template<class C2>
1830b57cec5SDimitry Andric      void merge(multimap<Key, T, C2, Allocator>& source);    // C++17
1840b57cec5SDimitry Andric    template<class C2>
1850b57cec5SDimitry Andric      void merge(multimap<Key, T, C2, Allocator>&& source);   // C++17
1860b57cec5SDimitry Andric
1870b57cec5SDimitry Andric    void swap(map& m)
1880b57cec5SDimitry Andric        noexcept(allocator_traits<allocator_type>::is_always_equal::value &&
1890b57cec5SDimitry Andric            is_nothrow_swappable<key_compare>::value); // C++17
1900b57cec5SDimitry Andric
1910b57cec5SDimitry Andric    // observers:
1920b57cec5SDimitry Andric    allocator_type get_allocator() const noexcept;
1930b57cec5SDimitry Andric    key_compare    key_comp()      const;
1940b57cec5SDimitry Andric    value_compare  value_comp()    const;
1950b57cec5SDimitry Andric
1960b57cec5SDimitry Andric    // map operations:
1970b57cec5SDimitry Andric          iterator find(const key_type& k);
1980b57cec5SDimitry Andric    const_iterator find(const key_type& k) const;
1990b57cec5SDimitry Andric    template<typename K>
2000b57cec5SDimitry Andric        iterator find(const K& x);              // C++14
2010b57cec5SDimitry Andric    template<typename K>
2020b57cec5SDimitry Andric        const_iterator find(const K& x) const;  // C++14
203fe6060f1SDimitry Andric
2040b57cec5SDimitry Andric    template<typename K>
2050b57cec5SDimitry Andric      size_type count(const K& x) const;        // C++14
2060b57cec5SDimitry Andric    size_type      count(const key_type& k) const;
207fe6060f1SDimitry Andric
2080b57cec5SDimitry Andric    bool           contains(const key_type& x) const;  // C++20
209fe6060f1SDimitry Andric    template<class K> bool contains(const K& x) const; // C++20
210fe6060f1SDimitry Andric
2110b57cec5SDimitry Andric          iterator lower_bound(const key_type& k);
2120b57cec5SDimitry Andric    const_iterator lower_bound(const key_type& k) const;
2130b57cec5SDimitry Andric    template<typename K>
2140b57cec5SDimitry Andric        iterator lower_bound(const K& x);              // C++14
2150b57cec5SDimitry Andric    template<typename K>
2160b57cec5SDimitry Andric        const_iterator lower_bound(const K& x) const;  // C++14
2170b57cec5SDimitry Andric
2180b57cec5SDimitry Andric          iterator upper_bound(const key_type& k);
2190b57cec5SDimitry Andric    const_iterator upper_bound(const key_type& k) const;
2200b57cec5SDimitry Andric    template<typename K>
2210b57cec5SDimitry Andric        iterator upper_bound(const K& x);              // C++14
2220b57cec5SDimitry Andric    template<typename K>
2230b57cec5SDimitry Andric        const_iterator upper_bound(const K& x) const;  // C++14
2240b57cec5SDimitry Andric
2250b57cec5SDimitry Andric    pair<iterator,iterator>             equal_range(const key_type& k);
2260b57cec5SDimitry Andric    pair<const_iterator,const_iterator> equal_range(const key_type& k) const;
2270b57cec5SDimitry Andric    template<typename K>
2280b57cec5SDimitry Andric        pair<iterator,iterator>             equal_range(const K& x);        // C++14
2290b57cec5SDimitry Andric    template<typename K>
2300b57cec5SDimitry Andric        pair<const_iterator,const_iterator> equal_range(const K& x) const;  // C++14
2310b57cec5SDimitry Andric};
2320b57cec5SDimitry Andric
233349cc55cSDimitry Andrictemplate <class InputIterator,
234349cc55cSDimitry Andric      class Compare = less<iter_key_t<InputIterator>>,
235349cc55cSDimitry Andric      class Allocator = allocator<iter_to_alloc_t<InputIterator>>>
236349cc55cSDimitry Andricmap(InputIterator, InputIterator, Compare = Compare(), Allocator = Allocator())
237349cc55cSDimitry Andric  -> map<iter_key_t<InputIterator>, iter_val_t<InputIterator>, Compare, Allocator>; // C++17
238349cc55cSDimitry Andric
23906c3fb27SDimitry Andrictemplate<ranges::input_range R, class Compare = less<range-key-type<R>,
24006c3fb27SDimitry Andric         class Allocator = allocator<range-to-alloc-type<R>>>
24106c3fb27SDimitry Andric  map(from_range_t, R&&, Compare = Compare(), Allocator = Allocator())
24206c3fb27SDimitry Andric    -> map<range-key-type<R>, range-mapped-type<R>, Compare, Allocator>; // C++23
24306c3fb27SDimitry Andric
244349cc55cSDimitry Andrictemplate<class Key, class T, class Compare = less<Key>,
245349cc55cSDimitry Andric    class Allocator = allocator<pair<const Key, T>>>
246349cc55cSDimitry Andricmap(initializer_list<pair<const Key, T>>, Compare = Compare(), Allocator = Allocator())
247349cc55cSDimitry Andric  -> map<Key, T, Compare, Allocator>; // C++17
248349cc55cSDimitry Andric
249349cc55cSDimitry Andrictemplate <class InputIterator, class Allocator>
250349cc55cSDimitry Andricmap(InputIterator, InputIterator, Allocator)
251349cc55cSDimitry Andric  -> map<iter_key_t<InputIterator>, iter_val_t<InputIterator>, less<iter_key_t<InputIterator>>,
252349cc55cSDimitry Andric    Allocator>; // C++17
253349cc55cSDimitry Andric
25406c3fb27SDimitry Andrictemplate<ranges::input_range R, class Allocator>
25506c3fb27SDimitry Andric  map(from_range_t, R&&, Allocator)
25606c3fb27SDimitry Andric    -> map<range-key-type<R>, range-mapped-type<R>, less<range-key-type<R>>, Allocator>; // C++23
25706c3fb27SDimitry Andric
258349cc55cSDimitry Andrictemplate<class Key, class T, class Allocator>
259349cc55cSDimitry Andricmap(initializer_list<pair<const Key, T>>, Allocator) -> map<Key, T, less<Key>, Allocator>; // C++17
260349cc55cSDimitry Andric
2610b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
2620b57cec5SDimitry Andricbool
2630b57cec5SDimitry Andricoperator==(const map<Key, T, Compare, Allocator>& x,
2640b57cec5SDimitry Andric           const map<Key, T, Compare, Allocator>& y);
2650b57cec5SDimitry Andric
2660b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
2670b57cec5SDimitry Andricbool
2680b57cec5SDimitry Andricoperator< (const map<Key, T, Compare, Allocator>& x,
26906c3fb27SDimitry Andric           const map<Key, T, Compare, Allocator>& y);      // removed in C++20
2700b57cec5SDimitry Andric
2710b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
2720b57cec5SDimitry Andricbool
2730b57cec5SDimitry Andricoperator!=(const map<Key, T, Compare, Allocator>& x,
27406c3fb27SDimitry Andric           const map<Key, T, Compare, Allocator>& y);      // removed in C++20
2750b57cec5SDimitry Andric
2760b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
2770b57cec5SDimitry Andricbool
2780b57cec5SDimitry Andricoperator> (const map<Key, T, Compare, Allocator>& x,
27906c3fb27SDimitry Andric           const map<Key, T, Compare, Allocator>& y);      // removed in C++20
2800b57cec5SDimitry Andric
2810b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
2820b57cec5SDimitry Andricbool
2830b57cec5SDimitry Andricoperator>=(const map<Key, T, Compare, Allocator>& x,
28406c3fb27SDimitry Andric           const map<Key, T, Compare, Allocator>& y);      // removed in C++20
2850b57cec5SDimitry Andric
2860b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
2870b57cec5SDimitry Andricbool
2880b57cec5SDimitry Andricoperator<=(const map<Key, T, Compare, Allocator>& x,
28906c3fb27SDimitry Andric           const map<Key, T, Compare, Allocator>& y);      // removed in C++20
29006c3fb27SDimitry Andric
29106c3fb27SDimitry Andrictemplate<class Key, class T, class Compare, class Allocator>
29206c3fb27SDimitry Andric  synth-three-way-result<pair<const Key, T>>
29306c3fb27SDimitry Andric    operator<=>(const map<Key, T, Compare, Allocator>& x,
29406c3fb27SDimitry Andric                const map<Key, T, Compare, Allocator>& y); // since C++20
2950b57cec5SDimitry Andric
2960b57cec5SDimitry Andric// specialized algorithms:
2970b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
2980b57cec5SDimitry Andricvoid
2990b57cec5SDimitry Andricswap(map<Key, T, Compare, Allocator>& x, map<Key, T, Compare, Allocator>& y)
3000b57cec5SDimitry Andric    noexcept(noexcept(x.swap(y)));
3010b57cec5SDimitry Andric
3020b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator, class Predicate>
3035ffd83dbSDimitry Andrictypename map<Key, T, Compare, Allocator>::size_type
3045ffd83dbSDimitry Andricerase_if(map<Key, T, Compare, Allocator>& c, Predicate pred);  // C++20
3050b57cec5SDimitry Andric
3060b57cec5SDimitry Andric
3070b57cec5SDimitry Andrictemplate <class Key, class T, class Compare = less<Key>,
3080b57cec5SDimitry Andric          class Allocator = allocator<pair<const Key, T>>>
3090b57cec5SDimitry Andricclass multimap
3100b57cec5SDimitry Andric{
3110b57cec5SDimitry Andricpublic:
3120b57cec5SDimitry Andric    // types:
3130b57cec5SDimitry Andric    typedef Key                                      key_type;
3140b57cec5SDimitry Andric    typedef T                                        mapped_type;
3150b57cec5SDimitry Andric    typedef pair<const key_type,mapped_type>         value_type;
3160b57cec5SDimitry Andric    typedef Compare                                  key_compare;
3170b57cec5SDimitry Andric    typedef Allocator                                allocator_type;
3180b57cec5SDimitry Andric    typedef typename allocator_type::reference       reference;
3190b57cec5SDimitry Andric    typedef typename allocator_type::const_reference const_reference;
3200b57cec5SDimitry Andric    typedef typename allocator_type::size_type       size_type;
3210b57cec5SDimitry Andric    typedef typename allocator_type::difference_type difference_type;
3220b57cec5SDimitry Andric    typedef typename allocator_type::pointer         pointer;
3230b57cec5SDimitry Andric    typedef typename allocator_type::const_pointer   const_pointer;
3240b57cec5SDimitry Andric
3250b57cec5SDimitry Andric    typedef implementation-defined                   iterator;
3260b57cec5SDimitry Andric    typedef implementation-defined                   const_iterator;
3270b57cec5SDimitry Andric    typedef std::reverse_iterator<iterator>          reverse_iterator;
3280b57cec5SDimitry Andric    typedef std::reverse_iterator<const_iterator>    const_reverse_iterator;
3290b57cec5SDimitry Andric    typedef unspecified                              node_type;              // C++17
3300b57cec5SDimitry Andric
3310b57cec5SDimitry Andric    class value_compare
3320b57cec5SDimitry Andric    {
3330b57cec5SDimitry Andric        friend class multimap;
3340b57cec5SDimitry Andric    protected:
3350b57cec5SDimitry Andric        key_compare comp;
3360b57cec5SDimitry Andric        value_compare(key_compare c);
3370b57cec5SDimitry Andric    public:
338fe6060f1SDimitry Andric        typedef bool result_type;  // deprecated in C++17, removed in C++20
339fe6060f1SDimitry Andric        typedef value_type first_argument_type;  // deprecated in C++17, removed in C++20
340fe6060f1SDimitry Andric        typedef value_type second_argument_type;  // deprecated in C++17, removed in C++20
3410b57cec5SDimitry Andric        bool operator()(const value_type& x, const value_type& y) const;
3420b57cec5SDimitry Andric    };
3430b57cec5SDimitry Andric
3440b57cec5SDimitry Andric    // construct/copy/destroy:
3450b57cec5SDimitry Andric    multimap()
3460b57cec5SDimitry Andric        noexcept(
3470b57cec5SDimitry Andric            is_nothrow_default_constructible<allocator_type>::value &&
3480b57cec5SDimitry Andric            is_nothrow_default_constructible<key_compare>::value &&
3490b57cec5SDimitry Andric            is_nothrow_copy_constructible<key_compare>::value);
3500b57cec5SDimitry Andric    explicit multimap(const key_compare& comp);
3510b57cec5SDimitry Andric    multimap(const key_compare& comp, const allocator_type& a);
3520b57cec5SDimitry Andric    template <class InputIterator>
3530b57cec5SDimitry Andric        multimap(InputIterator first, InputIterator last, const key_compare& comp);
3540b57cec5SDimitry Andric    template <class InputIterator>
3550b57cec5SDimitry Andric        multimap(InputIterator first, InputIterator last, const key_compare& comp,
3560b57cec5SDimitry Andric                 const allocator_type& a);
35706c3fb27SDimitry Andric    template<container-compatible-range<value_type> R>
35806c3fb27SDimitry Andric      multimap(from_range_t, R&& rg,
35906c3fb27SDimitry Andric               const Compare& comp = Compare(), const Allocator& = Allocator()); // C++23
3600b57cec5SDimitry Andric    multimap(const multimap& m);
3610b57cec5SDimitry Andric    multimap(multimap&& m)
3620b57cec5SDimitry Andric        noexcept(
3630b57cec5SDimitry Andric            is_nothrow_move_constructible<allocator_type>::value &&
3640b57cec5SDimitry Andric            is_nothrow_move_constructible<key_compare>::value);
3650b57cec5SDimitry Andric    explicit multimap(const allocator_type& a);
3660b57cec5SDimitry Andric    multimap(const multimap& m, const allocator_type& a);
3670b57cec5SDimitry Andric    multimap(multimap&& m, const allocator_type& a);
3680b57cec5SDimitry Andric    multimap(initializer_list<value_type> il, const key_compare& comp = key_compare());
3690b57cec5SDimitry Andric    multimap(initializer_list<value_type> il, const key_compare& comp,
3700b57cec5SDimitry Andric             const allocator_type& a);
3710b57cec5SDimitry Andric    template <class InputIterator>
3720b57cec5SDimitry Andric        multimap(InputIterator first, InputIterator last, const allocator_type& a)
3730b57cec5SDimitry Andric            : multimap(first, last, Compare(), a) {} // C++14
37406c3fb27SDimitry Andric    template<container-compatible-range<value_type> R>
37506c3fb27SDimitry Andric      multimap(from_range_t, R&& rg, const Allocator& a))
37606c3fb27SDimitry Andric        : multimap(from_range, std::forward<R>(rg), Compare(), a) { } // C++23
3770b57cec5SDimitry Andric    multimap(initializer_list<value_type> il, const allocator_type& a)
3780b57cec5SDimitry Andric        : multimap(il, Compare(), a) {} // C++14
3790b57cec5SDimitry Andric    ~multimap();
3800b57cec5SDimitry Andric
3810b57cec5SDimitry Andric    multimap& operator=(const multimap& m);
3820b57cec5SDimitry Andric    multimap& operator=(multimap&& m)
3830b57cec5SDimitry Andric        noexcept(
3840b57cec5SDimitry Andric            allocator_type::propagate_on_container_move_assignment::value &&
3850b57cec5SDimitry Andric            is_nothrow_move_assignable<allocator_type>::value &&
3860b57cec5SDimitry Andric            is_nothrow_move_assignable<key_compare>::value);
3870b57cec5SDimitry Andric    multimap& operator=(initializer_list<value_type> il);
3880b57cec5SDimitry Andric
3890b57cec5SDimitry Andric    // iterators:
3900b57cec5SDimitry Andric          iterator begin() noexcept;
3910b57cec5SDimitry Andric    const_iterator begin() const noexcept;
3920b57cec5SDimitry Andric          iterator end() noexcept;
3930b57cec5SDimitry Andric    const_iterator end()   const noexcept;
3940b57cec5SDimitry Andric
3950b57cec5SDimitry Andric          reverse_iterator rbegin() noexcept;
3960b57cec5SDimitry Andric    const_reverse_iterator rbegin() const noexcept;
3970b57cec5SDimitry Andric          reverse_iterator rend() noexcept;
3980b57cec5SDimitry Andric    const_reverse_iterator rend()   const noexcept;
3990b57cec5SDimitry Andric
4000b57cec5SDimitry Andric    const_iterator         cbegin()  const noexcept;
4010b57cec5SDimitry Andric    const_iterator         cend()    const noexcept;
4020b57cec5SDimitry Andric    const_reverse_iterator crbegin() const noexcept;
4030b57cec5SDimitry Andric    const_reverse_iterator crend()   const noexcept;
4040b57cec5SDimitry Andric
4050b57cec5SDimitry Andric    // capacity:
4060b57cec5SDimitry Andric    bool      empty()    const noexcept;
4070b57cec5SDimitry Andric    size_type size()     const noexcept;
4080b57cec5SDimitry Andric    size_type max_size() const noexcept;
4090b57cec5SDimitry Andric
4100b57cec5SDimitry Andric    // modifiers:
4110b57cec5SDimitry Andric    template <class... Args>
4120b57cec5SDimitry Andric        iterator emplace(Args&&... args);
4130b57cec5SDimitry Andric    template <class... Args>
4140b57cec5SDimitry Andric        iterator emplace_hint(const_iterator position, Args&&... args);
4150b57cec5SDimitry Andric    iterator insert(const value_type& v);
4160b57cec5SDimitry Andric    iterator insert(      value_type&& v);                                            // C++17
4170b57cec5SDimitry Andric    template <class P>
4180b57cec5SDimitry Andric        iterator insert(P&& p);
4190b57cec5SDimitry Andric    iterator insert(const_iterator position, const value_type& v);
4200b57cec5SDimitry Andric    iterator insert(const_iterator position,       value_type&& v);                   // C++17
4210b57cec5SDimitry Andric    template <class P>
4220b57cec5SDimitry Andric        iterator insert(const_iterator position, P&& p);
4230b57cec5SDimitry Andric    template <class InputIterator>
4240b57cec5SDimitry Andric        void insert(InputIterator first, InputIterator last);
42506c3fb27SDimitry Andric    template<container-compatible-range<value_type> R>
42606c3fb27SDimitry Andric      void insert_range(R&& rg);                                                      // C++23
4270b57cec5SDimitry Andric    void insert(initializer_list<value_type> il);
4280b57cec5SDimitry Andric
4290b57cec5SDimitry Andric    node_type extract(const_iterator position);                                       // C++17
4300b57cec5SDimitry Andric    node_type extract(const key_type& x);                                             // C++17
4310b57cec5SDimitry Andric    iterator insert(node_type&& nh);                                                  // C++17
4320b57cec5SDimitry Andric    iterator insert(const_iterator hint, node_type&& nh);                             // C++17
4330b57cec5SDimitry Andric
4340b57cec5SDimitry Andric    iterator  erase(const_iterator position);
4350b57cec5SDimitry Andric    iterator  erase(iterator position); // C++14
4360b57cec5SDimitry Andric    size_type erase(const key_type& k);
4370b57cec5SDimitry Andric    iterator  erase(const_iterator first, const_iterator last);
4380b57cec5SDimitry Andric    void clear() noexcept;
4390b57cec5SDimitry Andric
4400b57cec5SDimitry Andric    template<class C2>
4410b57cec5SDimitry Andric      void merge(multimap<Key, T, C2, Allocator>& source);    // C++17
4420b57cec5SDimitry Andric    template<class C2>
4430b57cec5SDimitry Andric      void merge(multimap<Key, T, C2, Allocator>&& source);   // C++17
4440b57cec5SDimitry Andric    template<class C2>
4450b57cec5SDimitry Andric      void merge(map<Key, T, C2, Allocator>& source);         // C++17
4460b57cec5SDimitry Andric    template<class C2>
4470b57cec5SDimitry Andric      void merge(map<Key, T, C2, Allocator>&& source);        // C++17
4480b57cec5SDimitry Andric
4490b57cec5SDimitry Andric    void swap(multimap& m)
4500b57cec5SDimitry Andric        noexcept(allocator_traits<allocator_type>::is_always_equal::value &&
4510b57cec5SDimitry Andric            is_nothrow_swappable<key_compare>::value); // C++17
4520b57cec5SDimitry Andric
4530b57cec5SDimitry Andric    // observers:
4540b57cec5SDimitry Andric    allocator_type get_allocator() const noexcept;
4550b57cec5SDimitry Andric    key_compare    key_comp()      const;
4560b57cec5SDimitry Andric    value_compare  value_comp()    const;
4570b57cec5SDimitry Andric
4580b57cec5SDimitry Andric    // map operations:
4590b57cec5SDimitry Andric          iterator find(const key_type& k);
4600b57cec5SDimitry Andric    const_iterator find(const key_type& k) const;
4610b57cec5SDimitry Andric    template<typename K>
4620b57cec5SDimitry Andric        iterator find(const K& x);              // C++14
4630b57cec5SDimitry Andric    template<typename K>
4640b57cec5SDimitry Andric        const_iterator find(const K& x) const;  // C++14
465fe6060f1SDimitry Andric
4660b57cec5SDimitry Andric    template<typename K>
4670b57cec5SDimitry Andric      size_type count(const K& x) const;        // C++14
4680b57cec5SDimitry Andric    size_type      count(const key_type& k) const;
469fe6060f1SDimitry Andric
4700b57cec5SDimitry Andric    bool           contains(const key_type& x) const;  // C++20
471fe6060f1SDimitry Andric    template<class K> bool contains(const K& x) const; // C++20
472fe6060f1SDimitry Andric
4730b57cec5SDimitry Andric          iterator lower_bound(const key_type& k);
4740b57cec5SDimitry Andric    const_iterator lower_bound(const key_type& k) const;
4750b57cec5SDimitry Andric    template<typename K>
4760b57cec5SDimitry Andric        iterator lower_bound(const K& x);              // C++14
4770b57cec5SDimitry Andric    template<typename K>
4780b57cec5SDimitry Andric        const_iterator lower_bound(const K& x) const;  // C++14
4790b57cec5SDimitry Andric
4800b57cec5SDimitry Andric          iterator upper_bound(const key_type& k);
4810b57cec5SDimitry Andric    const_iterator upper_bound(const key_type& k) const;
4820b57cec5SDimitry Andric    template<typename K>
4830b57cec5SDimitry Andric        iterator upper_bound(const K& x);              // C++14
4840b57cec5SDimitry Andric    template<typename K>
4850b57cec5SDimitry Andric        const_iterator upper_bound(const K& x) const;  // C++14
4860b57cec5SDimitry Andric
4870b57cec5SDimitry Andric    pair<iterator,iterator>             equal_range(const key_type& k);
4880b57cec5SDimitry Andric    pair<const_iterator,const_iterator> equal_range(const key_type& k) const;
4890b57cec5SDimitry Andric    template<typename K>
4900b57cec5SDimitry Andric        pair<iterator,iterator>             equal_range(const K& x);        // C++14
4910b57cec5SDimitry Andric    template<typename K>
4920b57cec5SDimitry Andric        pair<const_iterator,const_iterator> equal_range(const K& x) const;  // C++14
4930b57cec5SDimitry Andric};
4940b57cec5SDimitry Andric
495349cc55cSDimitry Andrictemplate <class InputIterator,
496349cc55cSDimitry Andric      class Compare = less<iter_key_t<InputIterator>>,
497349cc55cSDimitry Andric      class Allocator = allocator<iter_to_alloc_t<InputIterator>>>
498349cc55cSDimitry Andricmultimap(InputIterator, InputIterator, Compare = Compare(), Allocator = Allocator())
499349cc55cSDimitry Andric  -> multimap<iter_key_t<InputIterator>, iter_val_t<InputIterator>, Compare, Allocator>; // C++17
500349cc55cSDimitry Andric
50106c3fb27SDimitry Andrictemplate<ranges::input_range R, class Compare = less<range-key-type<R>>,
50206c3fb27SDimitry Andric          class Allocator = allocator<range-to-alloc-type<R>>>
50306c3fb27SDimitry Andric  multimap(from_range_t, R&&, Compare = Compare(), Allocator = Allocator())
50406c3fb27SDimitry Andric    -> multimap<range-key-type<R>, range-mapped-type<R>, Compare, Allocator>; // C++23
50506c3fb27SDimitry Andric
506349cc55cSDimitry Andrictemplate<class Key, class T, class Compare = less<Key>,
507349cc55cSDimitry Andric    class Allocator = allocator<pair<const Key, T>>>
508349cc55cSDimitry Andricmultimap(initializer_list<pair<const Key, T>>, Compare = Compare(), Allocator = Allocator())
509349cc55cSDimitry Andric  -> multimap<Key, T, Compare, Allocator>; // C++17
510349cc55cSDimitry Andric
511349cc55cSDimitry Andrictemplate <class InputIterator, class Allocator>
512349cc55cSDimitry Andricmultimap(InputIterator, InputIterator, Allocator)
513349cc55cSDimitry Andric  -> multimap<iter_key_t<InputIterator>, iter_val_t<InputIterator>,
514349cc55cSDimitry Andric    less<iter_key_t<InputIterator>>, Allocator>; // C++17
515349cc55cSDimitry Andric
51606c3fb27SDimitry Andrictemplate<ranges::input_range R, class Allocator>
51706c3fb27SDimitry Andric  multimap(from_range_t, R&&, Allocator)
51806c3fb27SDimitry Andric    -> multimap<range-key-type<R>, range-mapped-type<R>, less<range-key-type<R>>, Allocator>; // C++23
51906c3fb27SDimitry Andric
520349cc55cSDimitry Andrictemplate<class Key, class T, class Allocator>
521349cc55cSDimitry Andricmultimap(initializer_list<pair<const Key, T>>, Allocator)
522349cc55cSDimitry Andric  -> multimap<Key, T, less<Key>, Allocator>; // C++17
523349cc55cSDimitry Andric
5240b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
5250b57cec5SDimitry Andricbool
5260b57cec5SDimitry Andricoperator==(const multimap<Key, T, Compare, Allocator>& x,
5270b57cec5SDimitry Andric           const multimap<Key, T, Compare, Allocator>& y);
5280b57cec5SDimitry Andric
5290b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
5300b57cec5SDimitry Andricbool
5310b57cec5SDimitry Andricoperator< (const multimap<Key, T, Compare, Allocator>& x,
53206c3fb27SDimitry Andric           const multimap<Key, T, Compare, Allocator>& y);      // removed in C++20
5330b57cec5SDimitry Andric
5340b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
5350b57cec5SDimitry Andricbool
5360b57cec5SDimitry Andricoperator!=(const multimap<Key, T, Compare, Allocator>& x,
53706c3fb27SDimitry Andric           const multimap<Key, T, Compare, Allocator>& y);      // removed in C++20
5380b57cec5SDimitry Andric
5390b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
5400b57cec5SDimitry Andricbool
5410b57cec5SDimitry Andricoperator> (const multimap<Key, T, Compare, Allocator>& x,
54206c3fb27SDimitry Andric           const multimap<Key, T, Compare, Allocator>& y);      // removed in C++20
5430b57cec5SDimitry Andric
5440b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
5450b57cec5SDimitry Andricbool
5460b57cec5SDimitry Andricoperator>=(const multimap<Key, T, Compare, Allocator>& x,
54706c3fb27SDimitry Andric           const multimap<Key, T, Compare, Allocator>& y);      // removed in C++20
5480b57cec5SDimitry Andric
5490b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
5500b57cec5SDimitry Andricbool
5510b57cec5SDimitry Andricoperator<=(const multimap<Key, T, Compare, Allocator>& x,
55206c3fb27SDimitry Andric           const multimap<Key, T, Compare, Allocator>& y);      // removed in C++20
55306c3fb27SDimitry Andric
55406c3fb27SDimitry Andrictemplate<class Key, class T, class Compare, class Allocator>
55506c3fb27SDimitry Andric  synth-three-way-result<pair<const Key, T>>
55606c3fb27SDimitry Andric    operator<=>(const multimap<Key, T, Compare, Allocator>& x,
55706c3fb27SDimitry Andric                const multimap<Key, T, Compare, Allocator>& y); // since c++20
5580b57cec5SDimitry Andric
5590b57cec5SDimitry Andric// specialized algorithms:
5600b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator>
5610b57cec5SDimitry Andricvoid
5620b57cec5SDimitry Andricswap(multimap<Key, T, Compare, Allocator>& x,
5630b57cec5SDimitry Andric     multimap<Key, T, Compare, Allocator>& y)
5640b57cec5SDimitry Andric    noexcept(noexcept(x.swap(y)));
5650b57cec5SDimitry Andric
5660b57cec5SDimitry Andrictemplate <class Key, class T, class Compare, class Allocator, class Predicate>
5675ffd83dbSDimitry Andrictypename multimap<Key, T, Compare, Allocator>::size_type
5685ffd83dbSDimitry Andricerase_if(multimap<Key, T, Compare, Allocator>& c, Predicate pred);  // C++20
5690b57cec5SDimitry Andric
5700b57cec5SDimitry Andric}  // std
5710b57cec5SDimitry Andric
5720b57cec5SDimitry Andric*/
5730b57cec5SDimitry Andric
57481ad6265SDimitry Andric#include <__algorithm/equal.h>
57581ad6265SDimitry Andric#include <__algorithm/lexicographical_compare.h>
57606c3fb27SDimitry Andric#include <__algorithm/lexicographical_compare_three_way.h>
57781ad6265SDimitry Andric#include <__assert> // all public C++ headers provide the assertion handler
57806c3fb27SDimitry Andric#include <__availability>
5790b57cec5SDimitry Andric#include <__config>
58081ad6265SDimitry Andric#include <__functional/binary_function.h>
581fe6060f1SDimitry Andric#include <__functional/is_transparent.h>
58281ad6265SDimitry Andric#include <__functional/operations.h>
58381ad6265SDimitry Andric#include <__iterator/erase_if_container.h>
584349cc55cSDimitry Andric#include <__iterator/iterator_traits.h>
58506c3fb27SDimitry Andric#include <__iterator/ranges_iterator_traits.h>
58681ad6265SDimitry Andric#include <__iterator/reverse_iterator.h>
58706c3fb27SDimitry Andric#include <__memory/addressof.h>
588bdd1243dSDimitry Andric#include <__memory/allocator.h>
589bdd1243dSDimitry Andric#include <__memory_resource/polymorphic_allocator.h>
5900b57cec5SDimitry Andric#include <__node_handle>
59106c3fb27SDimitry Andric#include <__ranges/concepts.h>
59206c3fb27SDimitry Andric#include <__ranges/container_compatible_range.h>
59306c3fb27SDimitry Andric#include <__ranges/from_range.h>
594fe6060f1SDimitry Andric#include <__tree>
595bdd1243dSDimitry Andric#include <__type_traits/is_allocator.h>
596fe6060f1SDimitry Andric#include <__utility/forward.h>
597bdd1243dSDimitry Andric#include <__utility/piecewise_construct.h>
59881ad6265SDimitry Andric#include <__utility/swap.h>
599*5f757f3fSDimitry Andric#include <stdexcept>
600bdd1243dSDimitry Andric#include <tuple>
6010b57cec5SDimitry Andric#include <version>
6020b57cec5SDimitry Andric
60381ad6265SDimitry Andric// standard-mandated includes
60481ad6265SDimitry Andric
60581ad6265SDimitry Andric// [iterator.range]
60681ad6265SDimitry Andric#include <__iterator/access.h>
60781ad6265SDimitry Andric#include <__iterator/data.h>
60881ad6265SDimitry Andric#include <__iterator/empty.h>
60981ad6265SDimitry Andric#include <__iterator/reverse_access.h>
61081ad6265SDimitry Andric#include <__iterator/size.h>
61181ad6265SDimitry Andric
61281ad6265SDimitry Andric// [associative.map.syn]
61381ad6265SDimitry Andric#include <compare>
61481ad6265SDimitry Andric#include <initializer_list>
61581ad6265SDimitry Andric
6160b57cec5SDimitry Andric#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
6170b57cec5SDimitry Andric#  pragma GCC system_header
6180b57cec5SDimitry Andric#endif
6190b57cec5SDimitry Andric
6200b57cec5SDimitry Andric_LIBCPP_BEGIN_NAMESPACE_STD
6210b57cec5SDimitry Andric
6220b57cec5SDimitry Andrictemplate <class _Key, class _CP, class _Compare,
6230b57cec5SDimitry Andric          bool = is_empty<_Compare>::value && !__libcpp_is_final<_Compare>::value>
6240b57cec5SDimitry Andricclass __map_value_compare
6250b57cec5SDimitry Andric    : private _Compare
6260b57cec5SDimitry Andric{
6270b57cec5SDimitry Andricpublic:
628*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
6290b57cec5SDimitry Andric    __map_value_compare()
6300b57cec5SDimitry Andric        _NOEXCEPT_(is_nothrow_default_constructible<_Compare>::value)
6310b57cec5SDimitry Andric        : _Compare() {}
632*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
633753f127fSDimitry Andric    __map_value_compare(_Compare __c)
6340b57cec5SDimitry Andric        _NOEXCEPT_(is_nothrow_copy_constructible<_Compare>::value)
635753f127fSDimitry Andric        : _Compare(__c) {}
636*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
6370b57cec5SDimitry Andric    const _Compare& key_comp() const _NOEXCEPT {return *this;}
638*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
6390b57cec5SDimitry Andric    bool operator()(const _CP& __x, const _CP& __y) const
6400b57cec5SDimitry Andric        {return static_cast<const _Compare&>(*this)(__x.__get_value().first, __y.__get_value().first);}
641*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
6420b57cec5SDimitry Andric    bool operator()(const _CP& __x, const _Key& __y) const
6430b57cec5SDimitry Andric        {return static_cast<const _Compare&>(*this)(__x.__get_value().first, __y);}
644*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
6450b57cec5SDimitry Andric    bool operator()(const _Key& __x, const _CP& __y) const
6460b57cec5SDimitry Andric        {return static_cast<const _Compare&>(*this)(__x, __y.__get_value().first);}
64706c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI void swap(__map_value_compare& __y)
6480b57cec5SDimitry Andric        _NOEXCEPT_(__is_nothrow_swappable<_Compare>::value)
6490b57cec5SDimitry Andric    {
650*5f757f3fSDimitry Andric      using std::swap;
6510b57cec5SDimitry Andric      swap(static_cast<_Compare&>(*this), static_cast<_Compare&>(__y));
6520b57cec5SDimitry Andric    }
6530b57cec5SDimitry Andric
65406c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
6550b57cec5SDimitry Andric    template <typename _K2>
656*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
657349cc55cSDimitry Andric    bool operator()(const _K2& __x, const _CP& __y) const
6580b57cec5SDimitry Andric        {return static_cast<const _Compare&>(*this)(__x, __y.__get_value().first);}
6590b57cec5SDimitry Andric
6600b57cec5SDimitry Andric    template <typename _K2>
661*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
662349cc55cSDimitry Andric    bool operator()(const _CP& __x, const _K2& __y) const
6630b57cec5SDimitry Andric        {return static_cast<const _Compare&>(*this)(__x.__get_value().first, __y);}
6640b57cec5SDimitry Andric#endif
6650b57cec5SDimitry Andric};
6660b57cec5SDimitry Andric
6670b57cec5SDimitry Andrictemplate <class _Key, class _CP, class _Compare>
6680b57cec5SDimitry Andricclass __map_value_compare<_Key, _CP, _Compare, false>
6690b57cec5SDimitry Andric{
670bdd1243dSDimitry Andric    _Compare __comp_;
6710b57cec5SDimitry Andric
6720b57cec5SDimitry Andricpublic:
673*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
6740b57cec5SDimitry Andric    __map_value_compare()
6750b57cec5SDimitry Andric        _NOEXCEPT_(is_nothrow_default_constructible<_Compare>::value)
676bdd1243dSDimitry Andric        : __comp_() {}
677*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
678753f127fSDimitry Andric    __map_value_compare(_Compare __c)
6790b57cec5SDimitry Andric        _NOEXCEPT_(is_nothrow_copy_constructible<_Compare>::value)
680bdd1243dSDimitry Andric        : __comp_(__c) {}
681*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
682bdd1243dSDimitry Andric    const _Compare& key_comp() const _NOEXCEPT {return __comp_;}
6830b57cec5SDimitry Andric
684*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
6850b57cec5SDimitry Andric    bool operator()(const _CP& __x, const _CP& __y) const
686bdd1243dSDimitry Andric        {return __comp_(__x.__get_value().first, __y.__get_value().first);}
687*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
6880b57cec5SDimitry Andric    bool operator()(const _CP& __x, const _Key& __y) const
689bdd1243dSDimitry Andric        {return __comp_(__x.__get_value().first, __y);}
690*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
6910b57cec5SDimitry Andric    bool operator()(const _Key& __x, const _CP& __y) const
692bdd1243dSDimitry Andric        {return __comp_(__x, __y.__get_value().first);}
6930b57cec5SDimitry Andric    void swap(__map_value_compare& __y)
6940b57cec5SDimitry Andric        _NOEXCEPT_(__is_nothrow_swappable<_Compare>::value)
6950b57cec5SDimitry Andric    {
696*5f757f3fSDimitry Andric        using std::swap;
697bdd1243dSDimitry Andric        swap(__comp_, __y.__comp_);
6980b57cec5SDimitry Andric    }
6990b57cec5SDimitry Andric
70006c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
7010b57cec5SDimitry Andric    template <typename _K2>
702*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
703349cc55cSDimitry Andric    bool operator()(const _K2& __x, const _CP& __y) const
704bdd1243dSDimitry Andric        {return __comp_(__x, __y.__get_value().first);}
7050b57cec5SDimitry Andric
7060b57cec5SDimitry Andric    template <typename _K2>
707*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
708349cc55cSDimitry Andric    bool operator()(const _CP& __x, const _K2& __y) const
709bdd1243dSDimitry Andric        {return __comp_(__x.__get_value().first, __y);}
7100b57cec5SDimitry Andric#endif
7110b57cec5SDimitry Andric};
7120b57cec5SDimitry Andric
7130b57cec5SDimitry Andrictemplate <class _Key, class _CP, class _Compare, bool __b>
714*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
7150b57cec5SDimitry Andricvoid
7160b57cec5SDimitry Andricswap(__map_value_compare<_Key, _CP, _Compare, __b>& __x,
7170b57cec5SDimitry Andric     __map_value_compare<_Key, _CP, _Compare, __b>& __y)
7180b57cec5SDimitry Andric    _NOEXCEPT_(_NOEXCEPT_(__x.swap(__y)))
7190b57cec5SDimitry Andric{
7200b57cec5SDimitry Andric    __x.swap(__y);
7210b57cec5SDimitry Andric}
7220b57cec5SDimitry Andric
7230b57cec5SDimitry Andrictemplate <class _Allocator>
7240b57cec5SDimitry Andricclass __map_node_destructor
7250b57cec5SDimitry Andric{
7260b57cec5SDimitry Andric    typedef _Allocator                          allocator_type;
7270b57cec5SDimitry Andric    typedef allocator_traits<allocator_type>    __alloc_traits;
7280b57cec5SDimitry Andric
7290b57cec5SDimitry Andricpublic:
7300b57cec5SDimitry Andric    typedef typename __alloc_traits::pointer    pointer;
7310b57cec5SDimitry Andric
7320b57cec5SDimitry Andricprivate:
7330b57cec5SDimitry Andric    allocator_type& __na_;
7340b57cec5SDimitry Andric
7350b57cec5SDimitry Andric    __map_node_destructor& operator=(const __map_node_destructor&);
7360b57cec5SDimitry Andric
7370b57cec5SDimitry Andricpublic:
7380b57cec5SDimitry Andric    bool __first_constructed;
7390b57cec5SDimitry Andric    bool __second_constructed;
7400b57cec5SDimitry Andric
741*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
7420b57cec5SDimitry Andric    explicit __map_node_destructor(allocator_type& __na) _NOEXCEPT
7430b57cec5SDimitry Andric        : __na_(__na),
7440b57cec5SDimitry Andric          __first_constructed(false),
7450b57cec5SDimitry Andric          __second_constructed(false)
7460b57cec5SDimitry Andric        {}
7470b57cec5SDimitry Andric
7480b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG
749*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
7500b57cec5SDimitry Andric    __map_node_destructor(__tree_node_destructor<allocator_type>&& __x) _NOEXCEPT
7510b57cec5SDimitry Andric        : __na_(__x.__na_),
7520b57cec5SDimitry Andric          __first_constructed(__x.__value_constructed),
7530b57cec5SDimitry Andric          __second_constructed(__x.__value_constructed)
7540b57cec5SDimitry Andric        {
7550b57cec5SDimitry Andric            __x.__value_constructed = false;
7560b57cec5SDimitry Andric        }
7570b57cec5SDimitry Andric#endif // _LIBCPP_CXX03_LANG
7580b57cec5SDimitry Andric
759*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
7600b57cec5SDimitry Andric    void operator()(pointer __p) _NOEXCEPT
7610b57cec5SDimitry Andric    {
7620b57cec5SDimitry Andric        if (__second_constructed)
763*5f757f3fSDimitry Andric            __alloc_traits::destroy(__na_, std::addressof(__p->__value_.__get_value().second));
7640b57cec5SDimitry Andric        if (__first_constructed)
765*5f757f3fSDimitry Andric            __alloc_traits::destroy(__na_, std::addressof(__p->__value_.__get_value().first));
7660b57cec5SDimitry Andric        if (__p)
7670b57cec5SDimitry Andric            __alloc_traits::deallocate(__na_, __p, 1);
7680b57cec5SDimitry Andric    }
7690b57cec5SDimitry Andric};
7700b57cec5SDimitry Andric
7710b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
7720b57cec5SDimitry Andric    class map;
7730b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
7740b57cec5SDimitry Andric    class multimap;
7750b57cec5SDimitry Andrictemplate <class _TreeIterator> class __map_const_iterator;
7760b57cec5SDimitry Andric
7770b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG
7780b57cec5SDimitry Andric
7790b57cec5SDimitry Andrictemplate <class _Key, class _Tp>
780fe6060f1SDimitry Andricstruct _LIBCPP_STANDALONE_DEBUG __value_type
7810b57cec5SDimitry Andric{
7820b57cec5SDimitry Andric    typedef _Key                                     key_type;
7830b57cec5SDimitry Andric    typedef _Tp                                      mapped_type;
7840b57cec5SDimitry Andric    typedef pair<const key_type, mapped_type>        value_type;
7850b57cec5SDimitry Andric    typedef pair<key_type&, mapped_type&>            __nc_ref_pair_type;
7860b57cec5SDimitry Andric    typedef pair<key_type&&, mapped_type&&>          __nc_rref_pair_type;
7870b57cec5SDimitry Andric
7880b57cec5SDimitry Andricprivate:
789bdd1243dSDimitry Andric    value_type __cc_;
7900b57cec5SDimitry Andric
7910b57cec5SDimitry Andricpublic:
792*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
7930b57cec5SDimitry Andric    value_type& __get_value()
7940b57cec5SDimitry Andric    {
79506c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 17
796*5f757f3fSDimitry Andric        return *std::launder(std::addressof(__cc_));
7970b57cec5SDimitry Andric#else
798bdd1243dSDimitry Andric        return __cc_;
7990b57cec5SDimitry Andric#endif
8000b57cec5SDimitry Andric    }
8010b57cec5SDimitry Andric
802*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
8030b57cec5SDimitry Andric    const value_type& __get_value() const
8040b57cec5SDimitry Andric    {
80506c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 17
806*5f757f3fSDimitry Andric        return *std::launder(std::addressof(__cc_));
8070b57cec5SDimitry Andric#else
808bdd1243dSDimitry Andric        return __cc_;
8090b57cec5SDimitry Andric#endif
8100b57cec5SDimitry Andric    }
8110b57cec5SDimitry Andric
812*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
8130b57cec5SDimitry Andric    __nc_ref_pair_type __ref()
8140b57cec5SDimitry Andric    {
8150b57cec5SDimitry Andric        value_type& __v = __get_value();
8160b57cec5SDimitry Andric        return __nc_ref_pair_type(const_cast<key_type&>(__v.first), __v.second);
8170b57cec5SDimitry Andric    }
8180b57cec5SDimitry Andric
819*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
8200b57cec5SDimitry Andric    __nc_rref_pair_type __move()
8210b57cec5SDimitry Andric    {
8220b57cec5SDimitry Andric        value_type& __v = __get_value();
8230b57cec5SDimitry Andric        return __nc_rref_pair_type(
824*5f757f3fSDimitry Andric            std::move(const_cast<key_type&>(__v.first)),
825*5f757f3fSDimitry Andric            std::move(__v.second));
8260b57cec5SDimitry Andric    }
8270b57cec5SDimitry Andric
828*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
8290b57cec5SDimitry Andric    __value_type& operator=(const __value_type& __v)
8300b57cec5SDimitry Andric    {
8310b57cec5SDimitry Andric        __ref() = __v.__get_value();
8320b57cec5SDimitry Andric        return *this;
8330b57cec5SDimitry Andric    }
8340b57cec5SDimitry Andric
835*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
8360b57cec5SDimitry Andric    __value_type& operator=(__value_type&& __v)
8370b57cec5SDimitry Andric    {
8380b57cec5SDimitry Andric        __ref() = __v.__move();
8390b57cec5SDimitry Andric        return *this;
8400b57cec5SDimitry Andric    }
8410b57cec5SDimitry Andric
8420b57cec5SDimitry Andric    template <class _ValueTp,
843753f127fSDimitry Andric              class = __enable_if_t<__is_same_uncvref<_ValueTp, value_type>::value>
8440b57cec5SDimitry Andric             >
845*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
8460b57cec5SDimitry Andric    __value_type& operator=(_ValueTp&& __v)
8470b57cec5SDimitry Andric    {
848*5f757f3fSDimitry Andric        __ref() = std::forward<_ValueTp>(__v);
8490b57cec5SDimitry Andric        return *this;
8500b57cec5SDimitry Andric    }
8510b57cec5SDimitry Andric
8520b57cec5SDimitry Andricprivate:
853349cc55cSDimitry Andric    __value_type() = delete;
854349cc55cSDimitry Andric    ~__value_type() = delete;
855349cc55cSDimitry Andric    __value_type(const __value_type&) = delete;
856349cc55cSDimitry Andric    __value_type(__value_type&&) = delete;
8570b57cec5SDimitry Andric};
8580b57cec5SDimitry Andric
8590b57cec5SDimitry Andric#else
8600b57cec5SDimitry Andric
8610b57cec5SDimitry Andrictemplate <class _Key, class _Tp>
8620b57cec5SDimitry Andricstruct __value_type
8630b57cec5SDimitry Andric{
8640b57cec5SDimitry Andric    typedef _Key                                     key_type;
8650b57cec5SDimitry Andric    typedef _Tp                                      mapped_type;
8660b57cec5SDimitry Andric    typedef pair<const key_type, mapped_type>        value_type;
8670b57cec5SDimitry Andric
8680b57cec5SDimitry Andricprivate:
869bdd1243dSDimitry Andric    value_type __cc_;
8700b57cec5SDimitry Andric
8710b57cec5SDimitry Andricpublic:
872*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
873bdd1243dSDimitry Andric    value_type& __get_value() { return __cc_; }
874*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
875bdd1243dSDimitry Andric    const value_type& __get_value() const { return __cc_; }
8760b57cec5SDimitry Andric
8770b57cec5SDimitry Andricprivate:
8780b57cec5SDimitry Andric   __value_type();
8790b57cec5SDimitry Andric   __value_type(__value_type const&);
8800b57cec5SDimitry Andric   __value_type& operator=(__value_type const&);
8810b57cec5SDimitry Andric   ~__value_type();
8820b57cec5SDimitry Andric};
8830b57cec5SDimitry Andric
8840b57cec5SDimitry Andric#endif // _LIBCPP_CXX03_LANG
8850b57cec5SDimitry Andric
8860b57cec5SDimitry Andrictemplate <class _Tp>
8870b57cec5SDimitry Andricstruct __extract_key_value_types;
8880b57cec5SDimitry Andric
8890b57cec5SDimitry Andrictemplate <class _Key, class _Tp>
8900b57cec5SDimitry Andricstruct __extract_key_value_types<__value_type<_Key, _Tp> >
8910b57cec5SDimitry Andric{
8920b57cec5SDimitry Andric  typedef _Key const __key_type;
8930b57cec5SDimitry Andric  typedef _Tp        __mapped_type;
8940b57cec5SDimitry Andric};
8950b57cec5SDimitry Andric
8960b57cec5SDimitry Andrictemplate <class _TreeIterator>
8970b57cec5SDimitry Andricclass _LIBCPP_TEMPLATE_VIS __map_iterator
8980b57cec5SDimitry Andric{
8990b57cec5SDimitry Andric    typedef typename _TreeIterator::_NodeTypes                   _NodeTypes;
9000b57cec5SDimitry Andric    typedef typename _TreeIterator::__pointer_traits             __pointer_traits;
9010b57cec5SDimitry Andric
9020b57cec5SDimitry Andric    _TreeIterator __i_;
9030b57cec5SDimitry Andric
9040b57cec5SDimitry Andricpublic:
9050b57cec5SDimitry Andric    typedef bidirectional_iterator_tag                           iterator_category;
9060b57cec5SDimitry Andric    typedef typename _NodeTypes::__map_value_type                value_type;
9070b57cec5SDimitry Andric    typedef typename _TreeIterator::difference_type              difference_type;
9080b57cec5SDimitry Andric    typedef value_type&                                          reference;
9090b57cec5SDimitry Andric    typedef typename _NodeTypes::__map_value_type_pointer        pointer;
9100b57cec5SDimitry Andric
911*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9120b57cec5SDimitry Andric    __map_iterator() _NOEXCEPT {}
9130b57cec5SDimitry Andric
914*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9150b57cec5SDimitry Andric    __map_iterator(_TreeIterator __i) _NOEXCEPT : __i_(__i) {}
9160b57cec5SDimitry Andric
917*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9180b57cec5SDimitry Andric    reference operator*() const {return __i_->__get_value();}
919*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9200b57cec5SDimitry Andric    pointer operator->() const {return pointer_traits<pointer>::pointer_to(__i_->__get_value());}
9210b57cec5SDimitry Andric
922*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9230b57cec5SDimitry Andric    __map_iterator& operator++() {++__i_; return *this;}
924*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9250b57cec5SDimitry Andric    __map_iterator operator++(int)
9260b57cec5SDimitry Andric    {
9270b57cec5SDimitry Andric        __map_iterator __t(*this);
9280b57cec5SDimitry Andric        ++(*this);
9290b57cec5SDimitry Andric        return __t;
9300b57cec5SDimitry Andric    }
9310b57cec5SDimitry Andric
932*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9330b57cec5SDimitry Andric    __map_iterator& operator--() {--__i_; return *this;}
934*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9350b57cec5SDimitry Andric    __map_iterator operator--(int)
9360b57cec5SDimitry Andric    {
9370b57cec5SDimitry Andric        __map_iterator __t(*this);
9380b57cec5SDimitry Andric        --(*this);
9390b57cec5SDimitry Andric        return __t;
9400b57cec5SDimitry Andric    }
9410b57cec5SDimitry Andric
942*5f757f3fSDimitry Andric    friend _LIBCPP_HIDE_FROM_ABI
9430b57cec5SDimitry Andric    bool operator==(const __map_iterator& __x, const __map_iterator& __y)
9440b57cec5SDimitry Andric        {return __x.__i_ == __y.__i_;}
9450b57cec5SDimitry Andric    friend
946*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9470b57cec5SDimitry Andric    bool operator!=(const __map_iterator& __x, const __map_iterator& __y)
9480b57cec5SDimitry Andric        {return __x.__i_ != __y.__i_;}
9490b57cec5SDimitry Andric
9500b57cec5SDimitry Andric    template <class, class, class, class> friend class _LIBCPP_TEMPLATE_VIS map;
9510b57cec5SDimitry Andric    template <class, class, class, class> friend class _LIBCPP_TEMPLATE_VIS multimap;
9520b57cec5SDimitry Andric    template <class> friend class _LIBCPP_TEMPLATE_VIS __map_const_iterator;
9530b57cec5SDimitry Andric};
9540b57cec5SDimitry Andric
9550b57cec5SDimitry Andrictemplate <class _TreeIterator>
9560b57cec5SDimitry Andricclass _LIBCPP_TEMPLATE_VIS __map_const_iterator
9570b57cec5SDimitry Andric{
9580b57cec5SDimitry Andric    typedef typename _TreeIterator::_NodeTypes                   _NodeTypes;
9590b57cec5SDimitry Andric    typedef typename _TreeIterator::__pointer_traits             __pointer_traits;
9600b57cec5SDimitry Andric
9610b57cec5SDimitry Andric    _TreeIterator __i_;
9620b57cec5SDimitry Andric
9630b57cec5SDimitry Andricpublic:
9640b57cec5SDimitry Andric    typedef bidirectional_iterator_tag                           iterator_category;
9650b57cec5SDimitry Andric    typedef typename _NodeTypes::__map_value_type                value_type;
9660b57cec5SDimitry Andric    typedef typename _TreeIterator::difference_type              difference_type;
9670b57cec5SDimitry Andric    typedef const value_type&                                    reference;
9680b57cec5SDimitry Andric    typedef typename _NodeTypes::__const_map_value_type_pointer  pointer;
9690b57cec5SDimitry Andric
970*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9710b57cec5SDimitry Andric    __map_const_iterator() _NOEXCEPT {}
9720b57cec5SDimitry Andric
973*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9740b57cec5SDimitry Andric    __map_const_iterator(_TreeIterator __i) _NOEXCEPT : __i_(__i) {}
975*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9760b57cec5SDimitry Andric    __map_const_iterator(__map_iterator<
9770b57cec5SDimitry Andric        typename _TreeIterator::__non_const_iterator> __i) _NOEXCEPT
9780b57cec5SDimitry Andric        : __i_(__i.__i_) {}
9790b57cec5SDimitry Andric
980*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9810b57cec5SDimitry Andric    reference operator*() const {return __i_->__get_value();}
982*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9830b57cec5SDimitry Andric    pointer operator->() const {return pointer_traits<pointer>::pointer_to(__i_->__get_value());}
9840b57cec5SDimitry Andric
985*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9860b57cec5SDimitry Andric    __map_const_iterator& operator++() {++__i_; return *this;}
987*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9880b57cec5SDimitry Andric    __map_const_iterator operator++(int)
9890b57cec5SDimitry Andric    {
9900b57cec5SDimitry Andric        __map_const_iterator __t(*this);
9910b57cec5SDimitry Andric        ++(*this);
9920b57cec5SDimitry Andric        return __t;
9930b57cec5SDimitry Andric    }
9940b57cec5SDimitry Andric
995*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9960b57cec5SDimitry Andric    __map_const_iterator& operator--() {--__i_; return *this;}
997*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
9980b57cec5SDimitry Andric    __map_const_iterator operator--(int)
9990b57cec5SDimitry Andric    {
10000b57cec5SDimitry Andric        __map_const_iterator __t(*this);
10010b57cec5SDimitry Andric        --(*this);
10020b57cec5SDimitry Andric        return __t;
10030b57cec5SDimitry Andric    }
10040b57cec5SDimitry Andric
1005*5f757f3fSDimitry Andric    friend _LIBCPP_HIDE_FROM_ABI
10060b57cec5SDimitry Andric    bool operator==(const __map_const_iterator& __x, const __map_const_iterator& __y)
10070b57cec5SDimitry Andric        {return __x.__i_ == __y.__i_;}
1008*5f757f3fSDimitry Andric    friend _LIBCPP_HIDE_FROM_ABI
10090b57cec5SDimitry Andric    bool operator!=(const __map_const_iterator& __x, const __map_const_iterator& __y)
10100b57cec5SDimitry Andric        {return __x.__i_ != __y.__i_;}
10110b57cec5SDimitry Andric
10120b57cec5SDimitry Andric    template <class, class, class, class> friend class _LIBCPP_TEMPLATE_VIS map;
10130b57cec5SDimitry Andric    template <class, class, class, class> friend class _LIBCPP_TEMPLATE_VIS multimap;
10140b57cec5SDimitry Andric    template <class, class, class> friend class _LIBCPP_TEMPLATE_VIS __tree_const_iterator;
10150b57cec5SDimitry Andric};
10160b57cec5SDimitry Andric
10170b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare = less<_Key>,
10180b57cec5SDimitry Andric          class _Allocator = allocator<pair<const _Key, _Tp> > >
10190b57cec5SDimitry Andricclass _LIBCPP_TEMPLATE_VIS map
10200b57cec5SDimitry Andric{
10210b57cec5SDimitry Andricpublic:
10220b57cec5SDimitry Andric    // types:
10230b57cec5SDimitry Andric    typedef _Key                                     key_type;
10240b57cec5SDimitry Andric    typedef _Tp                                      mapped_type;
10250b57cec5SDimitry Andric    typedef pair<const key_type, mapped_type>        value_type;
102681ad6265SDimitry Andric    typedef __type_identity_t<_Compare>              key_compare;
102781ad6265SDimitry Andric    typedef __type_identity_t<_Allocator>            allocator_type;
10280b57cec5SDimitry Andric    typedef value_type&                              reference;
10290b57cec5SDimitry Andric    typedef const value_type&                        const_reference;
10300b57cec5SDimitry Andric
10310b57cec5SDimitry Andric    static_assert((is_same<typename allocator_type::value_type, value_type>::value),
10320b57cec5SDimitry Andric                  "Allocator::value_type must be same type as value_type");
10330b57cec5SDimitry Andric
10340b57cec5SDimitry Andric    class _LIBCPP_TEMPLATE_VIS value_compare
103581ad6265SDimitry Andric        : public __binary_function<value_type, value_type, bool>
10360b57cec5SDimitry Andric    {
10370b57cec5SDimitry Andric        friend class map;
10380b57cec5SDimitry Andric    protected:
10390b57cec5SDimitry Andric        key_compare comp;
10400b57cec5SDimitry Andric
1041*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI value_compare(key_compare __c) : comp(__c) {}
10420b57cec5SDimitry Andric    public:
1043*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
10440b57cec5SDimitry Andric        bool operator()(const value_type& __x, const value_type& __y) const
10450b57cec5SDimitry Andric            {return comp(__x.first, __y.first);}
10460b57cec5SDimitry Andric    };
10470b57cec5SDimitry Andric
10480b57cec5SDimitry Andricprivate:
10490b57cec5SDimitry Andric
1050*5f757f3fSDimitry Andric    typedef std::__value_type<key_type, mapped_type>             __value_type;
10510b57cec5SDimitry Andric    typedef __map_value_compare<key_type, __value_type, key_compare> __vc;
1052bdd1243dSDimitry Andric    typedef __rebind_alloc<allocator_traits<allocator_type>, __value_type> __allocator_type;
10530b57cec5SDimitry Andric    typedef __tree<__value_type, __vc, __allocator_type>   __base;
10540b57cec5SDimitry Andric    typedef typename __base::__node_traits                 __node_traits;
10550b57cec5SDimitry Andric    typedef allocator_traits<allocator_type>               __alloc_traits;
10560b57cec5SDimitry Andric
1057bdd1243dSDimitry Andric    static_assert(is_same<allocator_type, __rebind_alloc<__alloc_traits, value_type> >::value,
1058bdd1243dSDimitry Andric                  "[allocator.requirements] states that rebinding an allocator to the same type should result in the "
1059bdd1243dSDimitry Andric                  "original allocator");
1060bdd1243dSDimitry Andric
10610b57cec5SDimitry Andric    __base __tree_;
10620b57cec5SDimitry Andric
10630b57cec5SDimitry Andricpublic:
10640b57cec5SDimitry Andric    typedef typename __alloc_traits::pointer               pointer;
10650b57cec5SDimitry Andric    typedef typename __alloc_traits::const_pointer         const_pointer;
10660b57cec5SDimitry Andric    typedef typename __alloc_traits::size_type             size_type;
10670b57cec5SDimitry Andric    typedef typename __alloc_traits::difference_type       difference_type;
10680b57cec5SDimitry Andric    typedef __map_iterator<typename __base::iterator>             iterator;
10690b57cec5SDimitry Andric    typedef __map_const_iterator<typename __base::const_iterator> const_iterator;
1070*5f757f3fSDimitry Andric    typedef std::reverse_iterator<iterator>               reverse_iterator;
1071*5f757f3fSDimitry Andric    typedef std::reverse_iterator<const_iterator>         const_reverse_iterator;
10720b57cec5SDimitry Andric
107306c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 17
10740b57cec5SDimitry Andric    typedef __map_node_handle<typename __base::__node, allocator_type> node_type;
10750b57cec5SDimitry Andric    typedef __insert_return_type<iterator, node_type> insert_return_type;
10760b57cec5SDimitry Andric#endif
10770b57cec5SDimitry Andric
10780b57cec5SDimitry Andric    template <class _Key2, class _Value2, class _Comp2, class _Alloc2>
10790b57cec5SDimitry Andric        friend class _LIBCPP_TEMPLATE_VIS map;
10800b57cec5SDimitry Andric    template <class _Key2, class _Value2, class _Comp2, class _Alloc2>
10810b57cec5SDimitry Andric        friend class _LIBCPP_TEMPLATE_VIS multimap;
10820b57cec5SDimitry Andric
1083*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
10840b57cec5SDimitry Andric    map()
10850b57cec5SDimitry Andric        _NOEXCEPT_(
10860b57cec5SDimitry Andric            is_nothrow_default_constructible<allocator_type>::value &&
10870b57cec5SDimitry Andric            is_nothrow_default_constructible<key_compare>::value &&
10880b57cec5SDimitry Andric            is_nothrow_copy_constructible<key_compare>::value)
10890b57cec5SDimitry Andric        : __tree_(__vc(key_compare())) {}
10900b57cec5SDimitry Andric
1091*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
10920b57cec5SDimitry Andric    explicit map(const key_compare& __comp)
10930b57cec5SDimitry Andric        _NOEXCEPT_(
10940b57cec5SDimitry Andric            is_nothrow_default_constructible<allocator_type>::value &&
10950b57cec5SDimitry Andric            is_nothrow_copy_constructible<key_compare>::value)
10960b57cec5SDimitry Andric        : __tree_(__vc(__comp)) {}
10970b57cec5SDimitry Andric
1098*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
10990b57cec5SDimitry Andric    explicit map(const key_compare& __comp, const allocator_type& __a)
11000b57cec5SDimitry Andric        : __tree_(__vc(__comp), typename __base::allocator_type(__a)) {}
11010b57cec5SDimitry Andric
11020b57cec5SDimitry Andric    template <class _InputIterator>
1103*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
11040b57cec5SDimitry Andric        map(_InputIterator __f, _InputIterator __l,
11050b57cec5SDimitry Andric            const key_compare& __comp = key_compare())
11060b57cec5SDimitry Andric        : __tree_(__vc(__comp))
11070b57cec5SDimitry Andric        {
11080b57cec5SDimitry Andric            insert(__f, __l);
11090b57cec5SDimitry Andric        }
11100b57cec5SDimitry Andric
11110b57cec5SDimitry Andric    template <class _InputIterator>
1112*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
11130b57cec5SDimitry Andric        map(_InputIterator __f, _InputIterator __l,
11140b57cec5SDimitry Andric            const key_compare& __comp, const allocator_type& __a)
11150b57cec5SDimitry Andric        : __tree_(__vc(__comp), typename __base::allocator_type(__a))
11160b57cec5SDimitry Andric        {
11170b57cec5SDimitry Andric            insert(__f, __l);
11180b57cec5SDimitry Andric        }
11190b57cec5SDimitry Andric
112006c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 23
112106c3fb27SDimitry Andric    template <_ContainerCompatibleRange<value_type> _Range>
112206c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI
112306c3fb27SDimitry Andric    map(from_range_t, _Range&& __range, const key_compare& __comp = key_compare(),
112406c3fb27SDimitry Andric        const allocator_type& __a = allocator_type())
112506c3fb27SDimitry Andric      : __tree_(__vc(__comp), typename __base::allocator_type(__a)) {
112606c3fb27SDimitry Andric      insert_range(std::forward<_Range>(__range));
112706c3fb27SDimitry Andric    }
112806c3fb27SDimitry Andric#endif
112906c3fb27SDimitry Andric
113006c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
11310b57cec5SDimitry Andric    template <class _InputIterator>
1132*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
11330b57cec5SDimitry Andric    map(_InputIterator __f, _InputIterator __l, const allocator_type& __a)
11340b57cec5SDimitry Andric        : map(__f, __l, key_compare(), __a) {}
11350b57cec5SDimitry Andric#endif
11360b57cec5SDimitry Andric
113706c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 23
113806c3fb27SDimitry Andric    template <_ContainerCompatibleRange<value_type> _Range>
113906c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI
114006c3fb27SDimitry Andric    map(from_range_t, _Range&& __range, const allocator_type& __a)
114106c3fb27SDimitry Andric      : map(from_range, std::forward<_Range>(__range), key_compare(), __a) {}
114206c3fb27SDimitry Andric#endif
114306c3fb27SDimitry Andric
1144*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
11450b57cec5SDimitry Andric    map(const map& __m)
11460b57cec5SDimitry Andric        : __tree_(__m.__tree_)
11470b57cec5SDimitry Andric        {
11480b57cec5SDimitry Andric            insert(__m.begin(), __m.end());
11490b57cec5SDimitry Andric        }
11500b57cec5SDimitry Andric
1151*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
11520b57cec5SDimitry Andric    map& operator=(const map& __m)
11530b57cec5SDimitry Andric        {
11540b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG
11550b57cec5SDimitry Andric            __tree_ = __m.__tree_;
11560b57cec5SDimitry Andric#else
1157*5f757f3fSDimitry Andric            if (this != std::addressof(__m)) {
11580b57cec5SDimitry Andric                __tree_.clear();
11590b57cec5SDimitry Andric                __tree_.value_comp() = __m.__tree_.value_comp();
11600b57cec5SDimitry Andric                __tree_.__copy_assign_alloc(__m.__tree_);
11610b57cec5SDimitry Andric                insert(__m.begin(), __m.end());
11620b57cec5SDimitry Andric            }
11630b57cec5SDimitry Andric#endif
11640b57cec5SDimitry Andric            return *this;
11650b57cec5SDimitry Andric        }
11660b57cec5SDimitry Andric
11670b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG
11680b57cec5SDimitry Andric
1169*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
11700b57cec5SDimitry Andric    map(map&& __m)
11710b57cec5SDimitry Andric        _NOEXCEPT_(is_nothrow_move_constructible<__base>::value)
1172*5f757f3fSDimitry Andric        : __tree_(std::move(__m.__tree_))
11730b57cec5SDimitry Andric        {
11740b57cec5SDimitry Andric        }
11750b57cec5SDimitry Andric
117606c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI map(map&& __m, const allocator_type& __a);
11770b57cec5SDimitry Andric
1178*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
11790b57cec5SDimitry Andric    map& operator=(map&& __m)
11800b57cec5SDimitry Andric        _NOEXCEPT_(is_nothrow_move_assignable<__base>::value)
11810b57cec5SDimitry Andric        {
1182*5f757f3fSDimitry Andric            __tree_ = std::move(__m.__tree_);
11830b57cec5SDimitry Andric            return *this;
11840b57cec5SDimitry Andric        }
11850b57cec5SDimitry Andric
1186*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
11870b57cec5SDimitry Andric    map(initializer_list<value_type> __il, const key_compare& __comp = key_compare())
11880b57cec5SDimitry Andric        : __tree_(__vc(__comp))
11890b57cec5SDimitry Andric        {
11900b57cec5SDimitry Andric            insert(__il.begin(), __il.end());
11910b57cec5SDimitry Andric        }
11920b57cec5SDimitry Andric
1193*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
11940b57cec5SDimitry Andric    map(initializer_list<value_type> __il, const key_compare& __comp, const allocator_type& __a)
11950b57cec5SDimitry Andric        : __tree_(__vc(__comp), typename __base::allocator_type(__a))
11960b57cec5SDimitry Andric        {
11970b57cec5SDimitry Andric            insert(__il.begin(), __il.end());
11980b57cec5SDimitry Andric        }
11990b57cec5SDimitry Andric
120006c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
1201*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12020b57cec5SDimitry Andric    map(initializer_list<value_type> __il, const allocator_type& __a)
12030b57cec5SDimitry Andric        : map(__il, key_compare(), __a) {}
12040b57cec5SDimitry Andric#endif
12050b57cec5SDimitry Andric
1206*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12070b57cec5SDimitry Andric    map& operator=(initializer_list<value_type> __il)
12080b57cec5SDimitry Andric        {
12090b57cec5SDimitry Andric            __tree_.__assign_unique(__il.begin(), __il.end());
12100b57cec5SDimitry Andric            return *this;
12110b57cec5SDimitry Andric        }
12120b57cec5SDimitry Andric
12130b57cec5SDimitry Andric#endif // _LIBCPP_CXX03_LANG
12140b57cec5SDimitry Andric
1215*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12160b57cec5SDimitry Andric    explicit map(const allocator_type& __a)
12170b57cec5SDimitry Andric        : __tree_(typename __base::allocator_type(__a))
12180b57cec5SDimitry Andric        {
12190b57cec5SDimitry Andric        }
12200b57cec5SDimitry Andric
1221*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12220b57cec5SDimitry Andric    map(const map& __m, const allocator_type& __a)
12230b57cec5SDimitry Andric        : __tree_(__m.__tree_.value_comp(), typename __base::allocator_type(__a))
12240b57cec5SDimitry Andric        {
12250b57cec5SDimitry Andric            insert(__m.begin(), __m.end());
12260b57cec5SDimitry Andric        }
12270b57cec5SDimitry Andric
1228*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12290b57cec5SDimitry Andric    ~map() {
12300b57cec5SDimitry Andric        static_assert(sizeof(__diagnose_non_const_comparator<_Key, _Compare>()), "");
12310b57cec5SDimitry Andric    }
12320b57cec5SDimitry Andric
1233*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12340b57cec5SDimitry Andric          iterator begin() _NOEXCEPT {return __tree_.begin();}
1235*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12360b57cec5SDimitry Andric    const_iterator begin() const _NOEXCEPT {return __tree_.begin();}
1237*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12380b57cec5SDimitry Andric          iterator end() _NOEXCEPT {return __tree_.end();}
1239*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12400b57cec5SDimitry Andric    const_iterator end() const _NOEXCEPT {return __tree_.end();}
12410b57cec5SDimitry Andric
1242*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12430b57cec5SDimitry Andric          reverse_iterator rbegin() _NOEXCEPT {return reverse_iterator(end());}
1244*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12450b57cec5SDimitry Andric    const_reverse_iterator rbegin() const _NOEXCEPT
12460b57cec5SDimitry Andric        {return const_reverse_iterator(end());}
1247*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12480b57cec5SDimitry Andric          reverse_iterator rend() _NOEXCEPT
12490b57cec5SDimitry Andric            {return       reverse_iterator(begin());}
1250*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12510b57cec5SDimitry Andric    const_reverse_iterator rend() const _NOEXCEPT
12520b57cec5SDimitry Andric        {return const_reverse_iterator(begin());}
12530b57cec5SDimitry Andric
1254*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12550b57cec5SDimitry Andric    const_iterator cbegin() const _NOEXCEPT {return begin();}
1256*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12570b57cec5SDimitry Andric    const_iterator cend() const _NOEXCEPT {return end();}
1258*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12590b57cec5SDimitry Andric    const_reverse_iterator crbegin() const _NOEXCEPT {return rbegin();}
1260*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12610b57cec5SDimitry Andric    const_reverse_iterator crend() const _NOEXCEPT {return rend();}
12620b57cec5SDimitry Andric
1263*5f757f3fSDimitry Andric    _LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_HIDE_FROM_ABI
12640b57cec5SDimitry Andric    bool      empty() const _NOEXCEPT {return __tree_.size() == 0;}
1265*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12660b57cec5SDimitry Andric    size_type size() const _NOEXCEPT {return __tree_.size();}
1267*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12680b57cec5SDimitry Andric    size_type max_size() const _NOEXCEPT {return __tree_.max_size();}
12690b57cec5SDimitry Andric
127006c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI mapped_type& operator[](const key_type& __k);
12710b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG
127206c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI mapped_type& operator[](key_type&& __k);
12730b57cec5SDimitry Andric#endif
12740b57cec5SDimitry Andric
127506c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI mapped_type& at(const key_type& __k);
127606c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI const mapped_type& at(const key_type& __k) const;
12770b57cec5SDimitry Andric
1278*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12790b57cec5SDimitry Andric    allocator_type get_allocator() const _NOEXCEPT {return allocator_type(__tree_.__alloc());}
1280*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12810b57cec5SDimitry Andric    key_compare    key_comp()      const {return __tree_.value_comp().key_comp();}
1282*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12830b57cec5SDimitry Andric    value_compare  value_comp()    const {return value_compare(__tree_.value_comp().key_comp());}
12840b57cec5SDimitry Andric
12850b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG
12860b57cec5SDimitry Andric    template <class ..._Args>
1287*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12880b57cec5SDimitry Andric    pair<iterator, bool> emplace(_Args&& ...__args) {
1289*5f757f3fSDimitry Andric        return __tree_.__emplace_unique(std::forward<_Args>(__args)...);
12900b57cec5SDimitry Andric    }
12910b57cec5SDimitry Andric
12920b57cec5SDimitry Andric    template <class ..._Args>
1293*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
12940b57cec5SDimitry Andric    iterator emplace_hint(const_iterator __p, _Args&& ...__args) {
1295*5f757f3fSDimitry Andric        return __tree_.__emplace_hint_unique(__p.__i_, std::forward<_Args>(__args)...);
12960b57cec5SDimitry Andric    }
12970b57cec5SDimitry Andric
12980b57cec5SDimitry Andric    template <class _Pp,
1299753f127fSDimitry Andric              class = __enable_if_t<is_constructible<value_type, _Pp>::value> >
1300*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
13010b57cec5SDimitry Andric        pair<iterator, bool> insert(_Pp&& __p)
1302*5f757f3fSDimitry Andric            {return __tree_.__insert_unique(std::forward<_Pp>(__p));}
13030b57cec5SDimitry Andric
13040b57cec5SDimitry Andric    template <class _Pp,
1305753f127fSDimitry Andric              class = __enable_if_t<is_constructible<value_type, _Pp>::value> >
1306*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
13070b57cec5SDimitry Andric        iterator insert(const_iterator __pos, _Pp&& __p)
1308*5f757f3fSDimitry Andric            {return __tree_.__insert_unique(__pos.__i_, std::forward<_Pp>(__p));}
13090b57cec5SDimitry Andric
13100b57cec5SDimitry Andric#endif // _LIBCPP_CXX03_LANG
13110b57cec5SDimitry Andric
1312*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
13130b57cec5SDimitry Andric    pair<iterator, bool>
13140b57cec5SDimitry Andric        insert(const value_type& __v) {return __tree_.__insert_unique(__v);}
13150b57cec5SDimitry Andric
1316*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
13170b57cec5SDimitry Andric    iterator
13180b57cec5SDimitry Andric        insert(const_iterator __p, const value_type& __v)
13190b57cec5SDimitry Andric            {return __tree_.__insert_unique(__p.__i_, __v);}
13200b57cec5SDimitry Andric
13210b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG
1322*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
13230b57cec5SDimitry Andric    pair<iterator, bool>
1324*5f757f3fSDimitry Andric    insert(value_type&& __v) {return __tree_.__insert_unique(std::move(__v));}
13250b57cec5SDimitry Andric
1326*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
13270b57cec5SDimitry Andric    iterator insert(const_iterator __p,  value_type&& __v)
1328*5f757f3fSDimitry Andric    {return __tree_.__insert_unique(__p.__i_, std::move(__v));}
13290b57cec5SDimitry Andric
1330*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
13310b57cec5SDimitry Andric    void insert(initializer_list<value_type> __il)
13320b57cec5SDimitry Andric        {insert(__il.begin(), __il.end());}
13330b57cec5SDimitry Andric#endif
13340b57cec5SDimitry Andric
13350b57cec5SDimitry Andric    template <class _InputIterator>
1336*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
13370b57cec5SDimitry Andric        void insert(_InputIterator __f, _InputIterator __l)
13380b57cec5SDimitry Andric        {
13390b57cec5SDimitry Andric            for (const_iterator __e = cend(); __f != __l; ++__f)
13400b57cec5SDimitry Andric                insert(__e.__i_, *__f);
13410b57cec5SDimitry Andric        }
13420b57cec5SDimitry Andric
134306c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 23
134406c3fb27SDimitry Andric    template <_ContainerCompatibleRange<value_type> _Range>
134506c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI
134606c3fb27SDimitry Andric    void insert_range(_Range&& __range) {
134706c3fb27SDimitry Andric      const_iterator __end = cend();
134806c3fb27SDimitry Andric      for (auto&& __element : __range) {
134906c3fb27SDimitry Andric        insert(__end.__i_, std::forward<decltype(__element)>(__element));
135006c3fb27SDimitry Andric      }
135106c3fb27SDimitry Andric    }
135206c3fb27SDimitry Andric#endif
135306c3fb27SDimitry Andric
135406c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 17
13550b57cec5SDimitry Andric
13560b57cec5SDimitry Andric    template <class... _Args>
1357*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
13580b57cec5SDimitry Andric        pair<iterator, bool> try_emplace(const key_type& __k, _Args&&... __args)
13590b57cec5SDimitry Andric    {
13600b57cec5SDimitry Andric        return __tree_.__emplace_unique_key_args(__k,
1361*5f757f3fSDimitry Andric            std::piecewise_construct,
1362*5f757f3fSDimitry Andric            std::forward_as_tuple(__k),
1363*5f757f3fSDimitry Andric            std::forward_as_tuple(std::forward<_Args>(__args)...));
13640b57cec5SDimitry Andric    }
13650b57cec5SDimitry Andric
13660b57cec5SDimitry Andric    template <class... _Args>
1367*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
13680b57cec5SDimitry Andric        pair<iterator, bool> try_emplace(key_type&& __k, _Args&&... __args)
13690b57cec5SDimitry Andric    {
13700b57cec5SDimitry Andric        return __tree_.__emplace_unique_key_args(__k,
1371*5f757f3fSDimitry Andric            std::piecewise_construct,
1372*5f757f3fSDimitry Andric            std::forward_as_tuple(std::move(__k)),
1373*5f757f3fSDimitry Andric            std::forward_as_tuple(std::forward<_Args>(__args)...));
13740b57cec5SDimitry Andric    }
13750b57cec5SDimitry Andric
13760b57cec5SDimitry Andric    template <class... _Args>
1377*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
13780b57cec5SDimitry Andric        iterator try_emplace(const_iterator __h, const key_type& __k, _Args&&... __args)
13790b57cec5SDimitry Andric    {
13800b57cec5SDimitry Andric        return __tree_.__emplace_hint_unique_key_args(__h.__i_, __k,
1381*5f757f3fSDimitry Andric            std::piecewise_construct,
1382*5f757f3fSDimitry Andric            std::forward_as_tuple(__k),
1383*5f757f3fSDimitry Andric            std::forward_as_tuple(std::forward<_Args>(__args)...)).first;
13840b57cec5SDimitry Andric    }
13850b57cec5SDimitry Andric
13860b57cec5SDimitry Andric    template <class... _Args>
1387*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
13880b57cec5SDimitry Andric        iterator try_emplace(const_iterator __h, key_type&& __k, _Args&&... __args)
13890b57cec5SDimitry Andric    {
13900b57cec5SDimitry Andric        return __tree_.__emplace_hint_unique_key_args(__h.__i_, __k,
1391*5f757f3fSDimitry Andric            std::piecewise_construct,
1392*5f757f3fSDimitry Andric            std::forward_as_tuple(std::move(__k)),
1393*5f757f3fSDimitry Andric            std::forward_as_tuple(std::forward<_Args>(__args)...)).first;
13940b57cec5SDimitry Andric    }
13950b57cec5SDimitry Andric
13960b57cec5SDimitry Andric    template <class _Vp>
1397*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
13980b57cec5SDimitry Andric        pair<iterator, bool> insert_or_assign(const key_type& __k, _Vp&& __v)
13990b57cec5SDimitry Andric    {
14000b57cec5SDimitry Andric        iterator __p = lower_bound(__k);
14010b57cec5SDimitry Andric        if ( __p != end() && !key_comp()(__k, __p->first))
14020b57cec5SDimitry Andric        {
1403*5f757f3fSDimitry Andric            __p->second = std::forward<_Vp>(__v);
1404*5f757f3fSDimitry Andric            return std::make_pair(__p, false);
14050b57cec5SDimitry Andric        }
1406*5f757f3fSDimitry Andric        return std::make_pair(emplace_hint(__p, __k, std::forward<_Vp>(__v)), true);
14070b57cec5SDimitry Andric    }
14080b57cec5SDimitry Andric
14090b57cec5SDimitry Andric    template <class _Vp>
1410*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
14110b57cec5SDimitry Andric        pair<iterator, bool> insert_or_assign(key_type&& __k, _Vp&& __v)
14120b57cec5SDimitry Andric    {
14130b57cec5SDimitry Andric        iterator __p = lower_bound(__k);
14140b57cec5SDimitry Andric        if ( __p != end() && !key_comp()(__k, __p->first))
14150b57cec5SDimitry Andric        {
1416*5f757f3fSDimitry Andric            __p->second = std::forward<_Vp>(__v);
1417*5f757f3fSDimitry Andric            return std::make_pair(__p, false);
14180b57cec5SDimitry Andric        }
1419*5f757f3fSDimitry Andric        return std::make_pair(emplace_hint(__p, std::move(__k), std::forward<_Vp>(__v)), true);
14200b57cec5SDimitry Andric    }
14210b57cec5SDimitry Andric
14220b57cec5SDimitry Andric    template <class _Vp>
1423*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI iterator insert_or_assign(const_iterator __h,
1424e8d8bef9SDimitry Andric                                                        const key_type& __k,
1425e8d8bef9SDimitry Andric                                                        _Vp&& __v) {
1426e8d8bef9SDimitry Andric      auto [__r, __inserted] = __tree_.__emplace_hint_unique_key_args(
1427*5f757f3fSDimitry Andric          __h.__i_, __k, __k, std::forward<_Vp>(__v));
1428e8d8bef9SDimitry Andric
1429e8d8bef9SDimitry Andric      if (!__inserted)
1430*5f757f3fSDimitry Andric        __r->__get_value().second = std::forward<_Vp>(__v);
1431e8d8bef9SDimitry Andric
1432e8d8bef9SDimitry Andric      return __r;
14330b57cec5SDimitry Andric    }
14340b57cec5SDimitry Andric
14350b57cec5SDimitry Andric    template <class _Vp>
1436*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI iterator insert_or_assign(const_iterator __h,
1437e8d8bef9SDimitry Andric                                                        key_type&& __k,
1438e8d8bef9SDimitry Andric                                                        _Vp&& __v) {
1439e8d8bef9SDimitry Andric      auto [__r, __inserted] = __tree_.__emplace_hint_unique_key_args(
1440*5f757f3fSDimitry Andric          __h.__i_, __k, std::move(__k), std::forward<_Vp>(__v));
1441e8d8bef9SDimitry Andric
1442e8d8bef9SDimitry Andric      if (!__inserted)
1443*5f757f3fSDimitry Andric        __r->__get_value().second = std::forward<_Vp>(__v);
1444e8d8bef9SDimitry Andric
1445e8d8bef9SDimitry Andric      return __r;
14460b57cec5SDimitry Andric    }
14470b57cec5SDimitry Andric
144806c3fb27SDimitry Andric#endif // _LIBCPP_STD_VER >= 17
14490b57cec5SDimitry Andric
1450*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
14510b57cec5SDimitry Andric    iterator erase(const_iterator __p) {return __tree_.erase(__p.__i_);}
1452*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
14530b57cec5SDimitry Andric    iterator erase(iterator __p)       {return __tree_.erase(__p.__i_);}
1454*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
14550b57cec5SDimitry Andric    size_type erase(const key_type& __k)
14560b57cec5SDimitry Andric        {return __tree_.__erase_unique(__k);}
1457*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
14580b57cec5SDimitry Andric    iterator  erase(const_iterator __f, const_iterator __l)
14590b57cec5SDimitry Andric        {return __tree_.erase(__f.__i_, __l.__i_);}
1460*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
14610b57cec5SDimitry Andric    void clear() _NOEXCEPT {__tree_.clear();}
14620b57cec5SDimitry Andric
146306c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 17
1464*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
14650b57cec5SDimitry Andric    insert_return_type insert(node_type&& __nh)
14660b57cec5SDimitry Andric    {
146706c3fb27SDimitry Andric        _LIBCPP_ASSERT_COMPATIBLE_ALLOCATOR(__nh.empty() || __nh.get_allocator() == get_allocator(),
14680b57cec5SDimitry Andric            "node_type with incompatible allocator passed to map::insert()");
14690b57cec5SDimitry Andric        return __tree_.template __node_handle_insert_unique<
1470*5f757f3fSDimitry Andric            node_type, insert_return_type>(std::move(__nh));
14710b57cec5SDimitry Andric    }
1472*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
14730b57cec5SDimitry Andric    iterator insert(const_iterator __hint, node_type&& __nh)
14740b57cec5SDimitry Andric    {
147506c3fb27SDimitry Andric        _LIBCPP_ASSERT_COMPATIBLE_ALLOCATOR(__nh.empty() || __nh.get_allocator() == get_allocator(),
14760b57cec5SDimitry Andric            "node_type with incompatible allocator passed to map::insert()");
14770b57cec5SDimitry Andric        return __tree_.template __node_handle_insert_unique<node_type>(
1478*5f757f3fSDimitry Andric            __hint.__i_, std::move(__nh));
14790b57cec5SDimitry Andric    }
1480*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
14810b57cec5SDimitry Andric    node_type extract(key_type const& __key)
14820b57cec5SDimitry Andric    {
14830b57cec5SDimitry Andric        return __tree_.template __node_handle_extract<node_type>(__key);
14840b57cec5SDimitry Andric    }
1485*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
14860b57cec5SDimitry Andric    node_type extract(const_iterator __it)
14870b57cec5SDimitry Andric    {
14880b57cec5SDimitry Andric        return __tree_.template __node_handle_extract<node_type>(__it.__i_);
14890b57cec5SDimitry Andric    }
14900b57cec5SDimitry Andric    template <class _Compare2>
1491*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
14920b57cec5SDimitry Andric    void merge(map<key_type, mapped_type, _Compare2, allocator_type>& __source)
14930b57cec5SDimitry Andric    {
149406c3fb27SDimitry Andric        _LIBCPP_ASSERT_COMPATIBLE_ALLOCATOR(__source.get_allocator() == get_allocator(),
14950b57cec5SDimitry Andric                                            "merging container with incompatible allocator");
14960b57cec5SDimitry Andric        __tree_.__node_handle_merge_unique(__source.__tree_);
14970b57cec5SDimitry Andric    }
14980b57cec5SDimitry Andric    template <class _Compare2>
1499*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
15000b57cec5SDimitry Andric    void merge(map<key_type, mapped_type, _Compare2, allocator_type>&& __source)
15010b57cec5SDimitry Andric    {
150206c3fb27SDimitry Andric        _LIBCPP_ASSERT_COMPATIBLE_ALLOCATOR(__source.get_allocator() == get_allocator(),
15030b57cec5SDimitry Andric                                            "merging container with incompatible allocator");
15040b57cec5SDimitry Andric        __tree_.__node_handle_merge_unique(__source.__tree_);
15050b57cec5SDimitry Andric    }
15060b57cec5SDimitry Andric    template <class _Compare2>
1507*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
15080b57cec5SDimitry Andric    void merge(multimap<key_type, mapped_type, _Compare2, allocator_type>& __source)
15090b57cec5SDimitry Andric    {
151006c3fb27SDimitry Andric        _LIBCPP_ASSERT_COMPATIBLE_ALLOCATOR(__source.get_allocator() == get_allocator(),
15110b57cec5SDimitry Andric                                            "merging container with incompatible allocator");
15120b57cec5SDimitry Andric        __tree_.__node_handle_merge_unique(__source.__tree_);
15130b57cec5SDimitry Andric    }
15140b57cec5SDimitry Andric    template <class _Compare2>
1515*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
15160b57cec5SDimitry Andric    void merge(multimap<key_type, mapped_type, _Compare2, allocator_type>&& __source)
15170b57cec5SDimitry Andric    {
151806c3fb27SDimitry Andric        _LIBCPP_ASSERT_COMPATIBLE_ALLOCATOR(__source.get_allocator() == get_allocator(),
15190b57cec5SDimitry Andric                                            "merging container with incompatible allocator");
15200b57cec5SDimitry Andric        __tree_.__node_handle_merge_unique(__source.__tree_);
15210b57cec5SDimitry Andric    }
15220b57cec5SDimitry Andric#endif
15230b57cec5SDimitry Andric
1524*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
15250b57cec5SDimitry Andric    void swap(map& __m)
15260b57cec5SDimitry Andric        _NOEXCEPT_(__is_nothrow_swappable<__base>::value)
15270b57cec5SDimitry Andric        {__tree_.swap(__m.__tree_);}
15280b57cec5SDimitry Andric
1529*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
15300b57cec5SDimitry Andric    iterator find(const key_type& __k)             {return __tree_.find(__k);}
1531*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
15320b57cec5SDimitry Andric    const_iterator find(const key_type& __k) const {return __tree_.find(__k);}
153306c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
1534*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
1535*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
1536*5f757f3fSDimitry Andric    iterator
15370b57cec5SDimitry Andric    find(const _K2& __k)                           {return __tree_.find(__k);}
1538*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
1539*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
1540*5f757f3fSDimitry Andric    const_iterator
15410b57cec5SDimitry Andric    find(const _K2& __k) const                     {return __tree_.find(__k);}
15420b57cec5SDimitry Andric#endif
15430b57cec5SDimitry Andric
1544*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
15450b57cec5SDimitry Andric    size_type      count(const key_type& __k) const
15460b57cec5SDimitry Andric        {return __tree_.__count_unique(__k);}
154706c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
1548*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
1549*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
1550*5f757f3fSDimitry Andric    size_type
15510b57cec5SDimitry Andric    count(const _K2& __k) const {return __tree_.__count_multi(__k);}
15520b57cec5SDimitry Andric#endif
15530b57cec5SDimitry Andric
155406c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 20
1555*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
15560b57cec5SDimitry Andric    bool contains(const key_type& __k) const {return find(__k) != end();}
1557*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
1558*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
1559*5f757f3fSDimitry Andric    bool
1560fe6060f1SDimitry Andric    contains(const _K2& __k) const { return find(__k) != end(); }
156106c3fb27SDimitry Andric#endif // _LIBCPP_STD_VER >= 20
15620b57cec5SDimitry Andric
1563*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
15640b57cec5SDimitry Andric    iterator lower_bound(const key_type& __k)
15650b57cec5SDimitry Andric        {return __tree_.lower_bound(__k);}
1566*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
15670b57cec5SDimitry Andric    const_iterator lower_bound(const key_type& __k) const
15680b57cec5SDimitry Andric        {return __tree_.lower_bound(__k);}
156906c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
1570*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
1571*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
1572*5f757f3fSDimitry Andric     iterator
15730b57cec5SDimitry Andric    lower_bound(const _K2& __k)       {return __tree_.lower_bound(__k);}
15740b57cec5SDimitry Andric
1575*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
1576*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
1577*5f757f3fSDimitry Andric     const_iterator
15780b57cec5SDimitry Andric    lower_bound(const _K2& __k) const {return __tree_.lower_bound(__k);}
15790b57cec5SDimitry Andric#endif
15800b57cec5SDimitry Andric
1581*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
15820b57cec5SDimitry Andric    iterator upper_bound(const key_type& __k)
15830b57cec5SDimitry Andric        {return __tree_.upper_bound(__k);}
1584*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
15850b57cec5SDimitry Andric    const_iterator upper_bound(const key_type& __k) const
15860b57cec5SDimitry Andric        {return __tree_.upper_bound(__k);}
158706c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
1588*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
1589*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
1590*5f757f3fSDimitry Andric     iterator
15910b57cec5SDimitry Andric    upper_bound(const _K2& __k)       {return __tree_.upper_bound(__k);}
1592*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
1593*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
1594*5f757f3fSDimitry Andric     const_iterator
15950b57cec5SDimitry Andric    upper_bound(const _K2& __k) const {return __tree_.upper_bound(__k);}
15960b57cec5SDimitry Andric#endif
15970b57cec5SDimitry Andric
1598*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
15990b57cec5SDimitry Andric    pair<iterator,iterator> equal_range(const key_type& __k)
16000b57cec5SDimitry Andric        {return __tree_.__equal_range_unique(__k);}
1601*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
16020b57cec5SDimitry Andric    pair<const_iterator,const_iterator> equal_range(const key_type& __k) const
16030b57cec5SDimitry Andric        {return __tree_.__equal_range_unique(__k);}
160406c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
1605*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
1606*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
1607*5f757f3fSDimitry Andric     pair<iterator,iterator>
16080b57cec5SDimitry Andric    equal_range(const _K2& __k)       {return __tree_.__equal_range_multi(__k);}
1609*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
1610*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
1611*5f757f3fSDimitry Andric     pair<const_iterator,const_iterator>
16120b57cec5SDimitry Andric    equal_range(const _K2& __k) const {return __tree_.__equal_range_multi(__k);}
16130b57cec5SDimitry Andric#endif
16140b57cec5SDimitry Andric
16150b57cec5SDimitry Andricprivate:
16160b57cec5SDimitry Andric    typedef typename __base::__node                    __node;
16170b57cec5SDimitry Andric    typedef typename __base::__node_allocator          __node_allocator;
16180b57cec5SDimitry Andric    typedef typename __base::__node_pointer            __node_pointer;
16190b57cec5SDimitry Andric    typedef typename __base::__node_base_pointer       __node_base_pointer;
16200b57cec5SDimitry Andric    typedef typename __base::__parent_pointer          __parent_pointer;
16210b57cec5SDimitry Andric
16220b57cec5SDimitry Andric    typedef __map_node_destructor<__node_allocator> _Dp;
16230b57cec5SDimitry Andric    typedef unique_ptr<__node, _Dp> __node_holder;
16240b57cec5SDimitry Andric
16250b57cec5SDimitry Andric#ifdef _LIBCPP_CXX03_LANG
162606c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI __node_holder __construct_node_with_key(const key_type& __k);
16270b57cec5SDimitry Andric#endif
16280b57cec5SDimitry Andric};
16290b57cec5SDimitry Andric
1630349cc55cSDimitry Andric#if _LIBCPP_STD_VER >= 17
16310b57cec5SDimitry Andrictemplate<class _InputIterator, class _Compare = less<__iter_key_type<_InputIterator>>,
16320b57cec5SDimitry Andric         class _Allocator = allocator<__iter_to_alloc_type<_InputIterator>>,
163306c3fb27SDimitry Andric         class = enable_if_t<__has_input_iterator_category<_InputIterator>::value, void>,
1634349cc55cSDimitry Andric         class = enable_if_t<!__is_allocator<_Compare>::value, void>,
1635349cc55cSDimitry Andric         class = enable_if_t<__is_allocator<_Allocator>::value, void>>
16360b57cec5SDimitry Andricmap(_InputIterator, _InputIterator, _Compare = _Compare(), _Allocator = _Allocator())
16370b57cec5SDimitry Andric  -> map<__iter_key_type<_InputIterator>, __iter_mapped_type<_InputIterator>, _Compare, _Allocator>;
16380b57cec5SDimitry Andric
163906c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 23
164006c3fb27SDimitry Andrictemplate <ranges::input_range _Range, class _Compare = less<__range_key_type<_Range>>,
164106c3fb27SDimitry Andric          class _Allocator = allocator<__range_to_alloc_type<_Range>>,
164206c3fb27SDimitry Andric          class = enable_if_t<!__is_allocator<_Compare>::value, void>,
164306c3fb27SDimitry Andric          class = enable_if_t<__is_allocator<_Allocator>::value, void>>
164406c3fb27SDimitry Andricmap(from_range_t, _Range&&, _Compare = _Compare(), _Allocator = _Allocator())
164506c3fb27SDimitry Andric  -> map<__range_key_type<_Range>, __range_mapped_type<_Range>, _Compare, _Allocator>;
164606c3fb27SDimitry Andric#endif
164706c3fb27SDimitry Andric
16480b57cec5SDimitry Andrictemplate<class _Key, class _Tp, class _Compare = less<remove_const_t<_Key>>,
16490b57cec5SDimitry Andric         class _Allocator = allocator<pair<const _Key, _Tp>>,
1650349cc55cSDimitry Andric         class = enable_if_t<!__is_allocator<_Compare>::value, void>,
1651349cc55cSDimitry Andric         class = enable_if_t<__is_allocator<_Allocator>::value, void>>
16520b57cec5SDimitry Andricmap(initializer_list<pair<_Key, _Tp>>, _Compare = _Compare(), _Allocator = _Allocator())
16530b57cec5SDimitry Andric  -> map<remove_const_t<_Key>, _Tp, _Compare, _Allocator>;
16540b57cec5SDimitry Andric
16550b57cec5SDimitry Andrictemplate<class _InputIterator, class _Allocator,
165606c3fb27SDimitry Andric         class = enable_if_t<__has_input_iterator_category<_InputIterator>::value, void>,
1657349cc55cSDimitry Andric         class = enable_if_t<__is_allocator<_Allocator>::value, void>>
16580b57cec5SDimitry Andricmap(_InputIterator, _InputIterator, _Allocator)
16590b57cec5SDimitry Andric  -> map<__iter_key_type<_InputIterator>, __iter_mapped_type<_InputIterator>,
16600b57cec5SDimitry Andric         less<__iter_key_type<_InputIterator>>, _Allocator>;
16610b57cec5SDimitry Andric
166206c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 23
166306c3fb27SDimitry Andrictemplate <ranges::input_range _Range, class _Allocator,
166406c3fb27SDimitry Andric          class = enable_if_t<__is_allocator<_Allocator>::value, void>>
166506c3fb27SDimitry Andricmap(from_range_t, _Range&&, _Allocator)
166606c3fb27SDimitry Andric  -> map<__range_key_type<_Range>, __range_mapped_type<_Range>, less<__range_key_type<_Range>>, _Allocator>;
166706c3fb27SDimitry Andric#endif
166806c3fb27SDimitry Andric
16690b57cec5SDimitry Andrictemplate<class _Key, class _Tp, class _Allocator,
1670349cc55cSDimitry Andric         class = enable_if_t<__is_allocator<_Allocator>::value, void>>
16710b57cec5SDimitry Andricmap(initializer_list<pair<_Key, _Tp>>, _Allocator)
16720b57cec5SDimitry Andric  -> map<remove_const_t<_Key>, _Tp, less<remove_const_t<_Key>>, _Allocator>;
16730b57cec5SDimitry Andric#endif
16740b57cec5SDimitry Andric
16750b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG
16760b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
16770b57cec5SDimitry Andricmap<_Key, _Tp, _Compare, _Allocator>::map(map&& __m, const allocator_type& __a)
1678*5f757f3fSDimitry Andric    : __tree_(std::move(__m.__tree_), typename __base::allocator_type(__a))
16790b57cec5SDimitry Andric{
16800b57cec5SDimitry Andric    if (__a != __m.get_allocator())
16810b57cec5SDimitry Andric    {
16820b57cec5SDimitry Andric        const_iterator __e = cend();
16830b57cec5SDimitry Andric        while (!__m.empty())
16840b57cec5SDimitry Andric            __tree_.__insert_unique(__e.__i_,
16850b57cec5SDimitry Andric                    __m.__tree_.remove(__m.begin().__i_)->__value_.__move());
16860b57cec5SDimitry Andric    }
16870b57cec5SDimitry Andric}
16880b57cec5SDimitry Andric
16890b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
16900b57cec5SDimitry Andric_Tp&
16910b57cec5SDimitry Andricmap<_Key, _Tp, _Compare, _Allocator>::operator[](const key_type& __k)
16920b57cec5SDimitry Andric{
16930b57cec5SDimitry Andric    return __tree_.__emplace_unique_key_args(__k,
1694*5f757f3fSDimitry Andric        std::piecewise_construct,
1695*5f757f3fSDimitry Andric        std::forward_as_tuple(__k),
1696*5f757f3fSDimitry Andric        std::forward_as_tuple()).first->__get_value().second;
16970b57cec5SDimitry Andric}
16980b57cec5SDimitry Andric
16990b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
17000b57cec5SDimitry Andric_Tp&
17010b57cec5SDimitry Andricmap<_Key, _Tp, _Compare, _Allocator>::operator[](key_type&& __k)
17020b57cec5SDimitry Andric{
1703*5f757f3fSDimitry Andric    // TODO investigate this clang-tidy warning.
1704*5f757f3fSDimitry Andric    // NOLINTNEXTLINE(bugprone-use-after-move)
17050b57cec5SDimitry Andric    return __tree_.__emplace_unique_key_args(__k,
1706*5f757f3fSDimitry Andric        std::piecewise_construct,
1707*5f757f3fSDimitry Andric        std::forward_as_tuple(std::move(__k)),
1708*5f757f3fSDimitry Andric        std::forward_as_tuple()).first->__get_value().second;
17090b57cec5SDimitry Andric}
17100b57cec5SDimitry Andric
17110b57cec5SDimitry Andric#else // _LIBCPP_CXX03_LANG
17120b57cec5SDimitry Andric
17130b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
17140b57cec5SDimitry Andrictypename map<_Key, _Tp, _Compare, _Allocator>::__node_holder
17150b57cec5SDimitry Andricmap<_Key, _Tp, _Compare, _Allocator>::__construct_node_with_key(const key_type& __k)
17160b57cec5SDimitry Andric{
17170b57cec5SDimitry Andric    __node_allocator& __na = __tree_.__node_alloc();
17180b57cec5SDimitry Andric    __node_holder __h(__node_traits::allocate(__na, 1), _Dp(__na));
1719*5f757f3fSDimitry Andric    __node_traits::construct(__na, std::addressof(__h->__value_.__get_value().first), __k);
17200b57cec5SDimitry Andric    __h.get_deleter().__first_constructed = true;
1721*5f757f3fSDimitry Andric    __node_traits::construct(__na, std::addressof(__h->__value_.__get_value().second));
17220b57cec5SDimitry Andric    __h.get_deleter().__second_constructed = true;
1723e8d8bef9SDimitry Andric    return __h;
17240b57cec5SDimitry Andric}
17250b57cec5SDimitry Andric
17260b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
17270b57cec5SDimitry Andric_Tp&
17280b57cec5SDimitry Andricmap<_Key, _Tp, _Compare, _Allocator>::operator[](const key_type& __k)
17290b57cec5SDimitry Andric{
17300b57cec5SDimitry Andric    __parent_pointer __parent;
17310b57cec5SDimitry Andric    __node_base_pointer& __child = __tree_.__find_equal(__parent, __k);
17320b57cec5SDimitry Andric    __node_pointer __r = static_cast<__node_pointer>(__child);
17330b57cec5SDimitry Andric    if (__child == nullptr)
17340b57cec5SDimitry Andric    {
17350b57cec5SDimitry Andric        __node_holder __h = __construct_node_with_key(__k);
17360b57cec5SDimitry Andric        __tree_.__insert_node_at(__parent, __child, static_cast<__node_base_pointer>(__h.get()));
17370b57cec5SDimitry Andric        __r = __h.release();
17380b57cec5SDimitry Andric    }
17390b57cec5SDimitry Andric    return __r->__value_.__get_value().second;
17400b57cec5SDimitry Andric}
17410b57cec5SDimitry Andric
17420b57cec5SDimitry Andric#endif // _LIBCPP_CXX03_LANG
17430b57cec5SDimitry Andric
17440b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
17450b57cec5SDimitry Andric_Tp&
17460b57cec5SDimitry Andricmap<_Key, _Tp, _Compare, _Allocator>::at(const key_type& __k)
17470b57cec5SDimitry Andric{
17480b57cec5SDimitry Andric    __parent_pointer __parent;
17490b57cec5SDimitry Andric    __node_base_pointer& __child = __tree_.__find_equal(__parent, __k);
17500b57cec5SDimitry Andric    if (__child == nullptr)
17510b57cec5SDimitry Andric        __throw_out_of_range("map::at:  key not found");
17520b57cec5SDimitry Andric    return static_cast<__node_pointer>(__child)->__value_.__get_value().second;
17530b57cec5SDimitry Andric}
17540b57cec5SDimitry Andric
17550b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
17560b57cec5SDimitry Andricconst _Tp&
17570b57cec5SDimitry Andricmap<_Key, _Tp, _Compare, _Allocator>::at(const key_type& __k) const
17580b57cec5SDimitry Andric{
17590b57cec5SDimitry Andric    __parent_pointer __parent;
17600b57cec5SDimitry Andric    __node_base_pointer __child = __tree_.__find_equal(__parent, __k);
17610b57cec5SDimitry Andric    if (__child == nullptr)
17620b57cec5SDimitry Andric        __throw_out_of_range("map::at:  key not found");
17630b57cec5SDimitry Andric    return static_cast<__node_pointer>(__child)->__value_.__get_value().second;
17640b57cec5SDimitry Andric}
17650b57cec5SDimitry Andric
17660b57cec5SDimitry Andric
17670b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
1768*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
17690b57cec5SDimitry Andricbool
17700b57cec5SDimitry Andricoperator==(const map<_Key, _Tp, _Compare, _Allocator>& __x,
17710b57cec5SDimitry Andric           const map<_Key, _Tp, _Compare, _Allocator>& __y)
17720b57cec5SDimitry Andric{
1773*5f757f3fSDimitry Andric    return __x.size() == __y.size() && std::equal(__x.begin(), __x.end(), __y.begin());
17740b57cec5SDimitry Andric}
17750b57cec5SDimitry Andric
177606c3fb27SDimitry Andric#if _LIBCPP_STD_VER <= 17
177706c3fb27SDimitry Andric
17780b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
1779*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
17800b57cec5SDimitry Andricbool
17810b57cec5SDimitry Andricoperator< (const map<_Key, _Tp, _Compare, _Allocator>& __x,
17820b57cec5SDimitry Andric           const map<_Key, _Tp, _Compare, _Allocator>& __y)
17830b57cec5SDimitry Andric{
1784*5f757f3fSDimitry Andric    return std::lexicographical_compare(__x.begin(), __x.end(), __y.begin(), __y.end());
17850b57cec5SDimitry Andric}
17860b57cec5SDimitry Andric
17870b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
1788*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
17890b57cec5SDimitry Andricbool
17900b57cec5SDimitry Andricoperator!=(const map<_Key, _Tp, _Compare, _Allocator>& __x,
17910b57cec5SDimitry Andric           const map<_Key, _Tp, _Compare, _Allocator>& __y)
17920b57cec5SDimitry Andric{
17930b57cec5SDimitry Andric    return !(__x == __y);
17940b57cec5SDimitry Andric}
17950b57cec5SDimitry Andric
17960b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
1797*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
17980b57cec5SDimitry Andricbool
17990b57cec5SDimitry Andricoperator> (const map<_Key, _Tp, _Compare, _Allocator>& __x,
18000b57cec5SDimitry Andric           const map<_Key, _Tp, _Compare, _Allocator>& __y)
18010b57cec5SDimitry Andric{
18020b57cec5SDimitry Andric    return __y < __x;
18030b57cec5SDimitry Andric}
18040b57cec5SDimitry Andric
18050b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
1806*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
18070b57cec5SDimitry Andricbool
18080b57cec5SDimitry Andricoperator>=(const map<_Key, _Tp, _Compare, _Allocator>& __x,
18090b57cec5SDimitry Andric           const map<_Key, _Tp, _Compare, _Allocator>& __y)
18100b57cec5SDimitry Andric{
18110b57cec5SDimitry Andric    return !(__x < __y);
18120b57cec5SDimitry Andric}
18130b57cec5SDimitry Andric
18140b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
1815*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
18160b57cec5SDimitry Andricbool
18170b57cec5SDimitry Andricoperator<=(const map<_Key, _Tp, _Compare, _Allocator>& __x,
18180b57cec5SDimitry Andric           const map<_Key, _Tp, _Compare, _Allocator>& __y)
18190b57cec5SDimitry Andric{
18200b57cec5SDimitry Andric    return !(__y < __x);
18210b57cec5SDimitry Andric}
18220b57cec5SDimitry Andric
182306c3fb27SDimitry Andric#else // #if _LIBCPP_STD_VER <= 17
182406c3fb27SDimitry Andric
182506c3fb27SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
182606c3fb27SDimitry Andric_LIBCPP_HIDE_FROM_ABI __synth_three_way_result<pair<const _Key, _Tp>>
182706c3fb27SDimitry Andricoperator<=>(const map<_Key, _Tp, _Compare, _Allocator>& __x, const map<_Key, _Tp, _Compare, _Allocator>& __y) {
182806c3fb27SDimitry Andric    return std::lexicographical_compare_three_way(
182906c3fb27SDimitry Andric        __x.begin(),
183006c3fb27SDimitry Andric        __x.end(),
183106c3fb27SDimitry Andric        __y.begin(),
183206c3fb27SDimitry Andric        __y.end(),
183306c3fb27SDimitry Andric        std::__synth_three_way<pair<const _Key, _Tp>, pair<const _Key, _Tp>>);
183406c3fb27SDimitry Andric}
183506c3fb27SDimitry Andric
183606c3fb27SDimitry Andric#endif // #if _LIBCPP_STD_VER <= 17
183706c3fb27SDimitry Andric
18380b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
1839*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
18400b57cec5SDimitry Andricvoid
18410b57cec5SDimitry Andricswap(map<_Key, _Tp, _Compare, _Allocator>& __x,
18420b57cec5SDimitry Andric     map<_Key, _Tp, _Compare, _Allocator>& __y)
18430b57cec5SDimitry Andric    _NOEXCEPT_(_NOEXCEPT_(__x.swap(__y)))
18440b57cec5SDimitry Andric{
18450b57cec5SDimitry Andric    __x.swap(__y);
18460b57cec5SDimitry Andric}
18470b57cec5SDimitry Andric
184806c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 20
18495ffd83dbSDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator,
18505ffd83dbSDimitry Andric          class _Predicate>
1851*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
18525ffd83dbSDimitry Andric    typename map<_Key, _Tp, _Compare, _Allocator>::size_type
18535ffd83dbSDimitry Andric    erase_if(map<_Key, _Tp, _Compare, _Allocator>& __c, _Predicate __pred) {
1854*5f757f3fSDimitry Andric  return std::__libcpp_erase_if_container(__c, __pred);
18555ffd83dbSDimitry Andric}
18560b57cec5SDimitry Andric#endif
18570b57cec5SDimitry Andric
18580b57cec5SDimitry Andric
18590b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare = less<_Key>,
18600b57cec5SDimitry Andric          class _Allocator = allocator<pair<const _Key, _Tp> > >
18610b57cec5SDimitry Andricclass _LIBCPP_TEMPLATE_VIS multimap
18620b57cec5SDimitry Andric{
18630b57cec5SDimitry Andricpublic:
18640b57cec5SDimitry Andric    // types:
18650b57cec5SDimitry Andric    typedef _Key                                     key_type;
18660b57cec5SDimitry Andric    typedef _Tp                                      mapped_type;
18670b57cec5SDimitry Andric    typedef pair<const key_type, mapped_type>        value_type;
186881ad6265SDimitry Andric    typedef __type_identity_t<_Compare>              key_compare;
186981ad6265SDimitry Andric    typedef __type_identity_t<_Allocator>            allocator_type;
18700b57cec5SDimitry Andric    typedef value_type&                              reference;
18710b57cec5SDimitry Andric    typedef const value_type&                        const_reference;
18720b57cec5SDimitry Andric
18730b57cec5SDimitry Andric    static_assert((is_same<typename allocator_type::value_type, value_type>::value),
18740b57cec5SDimitry Andric                  "Allocator::value_type must be same type as value_type");
18750b57cec5SDimitry Andric
18760b57cec5SDimitry Andric    class _LIBCPP_TEMPLATE_VIS value_compare
187781ad6265SDimitry Andric        : public __binary_function<value_type, value_type, bool>
18780b57cec5SDimitry Andric    {
18790b57cec5SDimitry Andric        friend class multimap;
18800b57cec5SDimitry Andric    protected:
18810b57cec5SDimitry Andric        key_compare comp;
18820b57cec5SDimitry Andric
1883*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
1884753f127fSDimitry Andric        value_compare(key_compare __c) : comp(__c) {}
18850b57cec5SDimitry Andric    public:
1886*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
18870b57cec5SDimitry Andric        bool operator()(const value_type& __x, const value_type& __y) const
18880b57cec5SDimitry Andric            {return comp(__x.first, __y.first);}
18890b57cec5SDimitry Andric    };
18900b57cec5SDimitry Andric
18910b57cec5SDimitry Andricprivate:
18920b57cec5SDimitry Andric
1893*5f757f3fSDimitry Andric    typedef std::__value_type<key_type, mapped_type>             __value_type;
18940b57cec5SDimitry Andric    typedef __map_value_compare<key_type, __value_type, key_compare> __vc;
1895bdd1243dSDimitry Andric    typedef __rebind_alloc<allocator_traits<allocator_type>, __value_type> __allocator_type;
18960b57cec5SDimitry Andric    typedef __tree<__value_type, __vc, __allocator_type>            __base;
18970b57cec5SDimitry Andric    typedef typename __base::__node_traits                          __node_traits;
18980b57cec5SDimitry Andric    typedef allocator_traits<allocator_type>                        __alloc_traits;
18990b57cec5SDimitry Andric
1900bdd1243dSDimitry Andric    static_assert(is_same<allocator_type, __rebind_alloc<__alloc_traits, value_type> >::value,
1901bdd1243dSDimitry Andric                  "[allocator.requirements] states that rebinding an allocator to the same type should result in the "
1902bdd1243dSDimitry Andric                  "original allocator");
1903bdd1243dSDimitry Andric
19040b57cec5SDimitry Andric    __base __tree_;
19050b57cec5SDimitry Andric
19060b57cec5SDimitry Andricpublic:
19070b57cec5SDimitry Andric    typedef typename __alloc_traits::pointer               pointer;
19080b57cec5SDimitry Andric    typedef typename __alloc_traits::const_pointer         const_pointer;
19090b57cec5SDimitry Andric    typedef typename __alloc_traits::size_type             size_type;
19100b57cec5SDimitry Andric    typedef typename __alloc_traits::difference_type       difference_type;
19110b57cec5SDimitry Andric    typedef __map_iterator<typename __base::iterator>      iterator;
19120b57cec5SDimitry Andric    typedef __map_const_iterator<typename __base::const_iterator> const_iterator;
1913*5f757f3fSDimitry Andric    typedef std::reverse_iterator<iterator>               reverse_iterator;
1914*5f757f3fSDimitry Andric    typedef std::reverse_iterator<const_iterator>         const_reverse_iterator;
19150b57cec5SDimitry Andric
191606c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 17
19170b57cec5SDimitry Andric    typedef __map_node_handle<typename __base::__node, allocator_type> node_type;
19180b57cec5SDimitry Andric#endif
19190b57cec5SDimitry Andric
19200b57cec5SDimitry Andric    template <class _Key2, class _Value2, class _Comp2, class _Alloc2>
19210b57cec5SDimitry Andric        friend class _LIBCPP_TEMPLATE_VIS map;
19220b57cec5SDimitry Andric    template <class _Key2, class _Value2, class _Comp2, class _Alloc2>
19230b57cec5SDimitry Andric        friend class _LIBCPP_TEMPLATE_VIS multimap;
19240b57cec5SDimitry Andric
1925*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
19260b57cec5SDimitry Andric    multimap()
19270b57cec5SDimitry Andric        _NOEXCEPT_(
19280b57cec5SDimitry Andric            is_nothrow_default_constructible<allocator_type>::value &&
19290b57cec5SDimitry Andric            is_nothrow_default_constructible<key_compare>::value &&
19300b57cec5SDimitry Andric            is_nothrow_copy_constructible<key_compare>::value)
19310b57cec5SDimitry Andric        : __tree_(__vc(key_compare())) {}
19320b57cec5SDimitry Andric
1933*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
19340b57cec5SDimitry Andric    explicit multimap(const key_compare& __comp)
19350b57cec5SDimitry Andric        _NOEXCEPT_(
19360b57cec5SDimitry Andric            is_nothrow_default_constructible<allocator_type>::value &&
19370b57cec5SDimitry Andric            is_nothrow_copy_constructible<key_compare>::value)
19380b57cec5SDimitry Andric        : __tree_(__vc(__comp)) {}
19390b57cec5SDimitry Andric
1940*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
19410b57cec5SDimitry Andric    explicit multimap(const key_compare& __comp, const allocator_type& __a)
19420b57cec5SDimitry Andric        : __tree_(__vc(__comp), typename __base::allocator_type(__a)) {}
19430b57cec5SDimitry Andric
19440b57cec5SDimitry Andric    template <class _InputIterator>
1945*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
19460b57cec5SDimitry Andric        multimap(_InputIterator __f, _InputIterator __l,
19470b57cec5SDimitry Andric            const key_compare& __comp = key_compare())
19480b57cec5SDimitry Andric        : __tree_(__vc(__comp))
19490b57cec5SDimitry Andric        {
19500b57cec5SDimitry Andric            insert(__f, __l);
19510b57cec5SDimitry Andric        }
19520b57cec5SDimitry Andric
19530b57cec5SDimitry Andric    template <class _InputIterator>
1954*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
19550b57cec5SDimitry Andric        multimap(_InputIterator __f, _InputIterator __l,
19560b57cec5SDimitry Andric            const key_compare& __comp, const allocator_type& __a)
19570b57cec5SDimitry Andric        : __tree_(__vc(__comp), typename __base::allocator_type(__a))
19580b57cec5SDimitry Andric        {
19590b57cec5SDimitry Andric            insert(__f, __l);
19600b57cec5SDimitry Andric        }
19610b57cec5SDimitry Andric
196206c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 23
196306c3fb27SDimitry Andric    template <_ContainerCompatibleRange<value_type> _Range>
196406c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI
196506c3fb27SDimitry Andric    multimap(from_range_t, _Range&& __range, const key_compare& __comp = key_compare(),
196606c3fb27SDimitry Andric        const allocator_type& __a = allocator_type())
196706c3fb27SDimitry Andric      : __tree_(__vc(__comp), typename __base::allocator_type(__a)) {
196806c3fb27SDimitry Andric      insert_range(std::forward<_Range>(__range));
196906c3fb27SDimitry Andric    }
197006c3fb27SDimitry Andric#endif
197106c3fb27SDimitry Andric
197206c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
19730b57cec5SDimitry Andric    template <class _InputIterator>
1974*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
19750b57cec5SDimitry Andric    multimap(_InputIterator __f, _InputIterator __l, const allocator_type& __a)
19760b57cec5SDimitry Andric        : multimap(__f, __l, key_compare(), __a) {}
19770b57cec5SDimitry Andric#endif
19780b57cec5SDimitry Andric
197906c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 23
198006c3fb27SDimitry Andric    template <_ContainerCompatibleRange<value_type> _Range>
198106c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI
198206c3fb27SDimitry Andric    multimap(from_range_t, _Range&& __range, const allocator_type& __a)
198306c3fb27SDimitry Andric      : multimap(from_range, std::forward<_Range>(__range), key_compare(), __a) {}
198406c3fb27SDimitry Andric#endif
198506c3fb27SDimitry Andric
1986*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
19870b57cec5SDimitry Andric    multimap(const multimap& __m)
19880b57cec5SDimitry Andric        : __tree_(__m.__tree_.value_comp(),
19890b57cec5SDimitry Andric          __alloc_traits::select_on_container_copy_construction(__m.__tree_.__alloc()))
19900b57cec5SDimitry Andric        {
19910b57cec5SDimitry Andric            insert(__m.begin(), __m.end());
19920b57cec5SDimitry Andric        }
19930b57cec5SDimitry Andric
1994*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
19950b57cec5SDimitry Andric    multimap& operator=(const multimap& __m)
19960b57cec5SDimitry Andric        {
19970b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG
19980b57cec5SDimitry Andric            __tree_ = __m.__tree_;
19990b57cec5SDimitry Andric#else
2000*5f757f3fSDimitry Andric            if (this != std::addressof(__m)) {
20010b57cec5SDimitry Andric                __tree_.clear();
20020b57cec5SDimitry Andric                __tree_.value_comp() = __m.__tree_.value_comp();
20030b57cec5SDimitry Andric                __tree_.__copy_assign_alloc(__m.__tree_);
20040b57cec5SDimitry Andric                insert(__m.begin(), __m.end());
20050b57cec5SDimitry Andric            }
20060b57cec5SDimitry Andric#endif
20070b57cec5SDimitry Andric            return *this;
20080b57cec5SDimitry Andric        }
20090b57cec5SDimitry Andric
20100b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG
20110b57cec5SDimitry Andric
2012*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20130b57cec5SDimitry Andric    multimap(multimap&& __m)
20140b57cec5SDimitry Andric        _NOEXCEPT_(is_nothrow_move_constructible<__base>::value)
2015*5f757f3fSDimitry Andric        : __tree_(std::move(__m.__tree_))
20160b57cec5SDimitry Andric        {
20170b57cec5SDimitry Andric        }
20180b57cec5SDimitry Andric
201906c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI multimap(multimap&& __m, const allocator_type& __a);
20200b57cec5SDimitry Andric
2021*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20220b57cec5SDimitry Andric    multimap& operator=(multimap&& __m)
20230b57cec5SDimitry Andric        _NOEXCEPT_(is_nothrow_move_assignable<__base>::value)
20240b57cec5SDimitry Andric        {
2025*5f757f3fSDimitry Andric            __tree_ = std::move(__m.__tree_);
20260b57cec5SDimitry Andric            return *this;
20270b57cec5SDimitry Andric        }
20280b57cec5SDimitry Andric
2029*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20300b57cec5SDimitry Andric    multimap(initializer_list<value_type> __il, const key_compare& __comp = key_compare())
20310b57cec5SDimitry Andric        : __tree_(__vc(__comp))
20320b57cec5SDimitry Andric        {
20330b57cec5SDimitry Andric            insert(__il.begin(), __il.end());
20340b57cec5SDimitry Andric        }
20350b57cec5SDimitry Andric
2036*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20370b57cec5SDimitry Andric    multimap(initializer_list<value_type> __il, const key_compare& __comp, const allocator_type& __a)
20380b57cec5SDimitry Andric        : __tree_(__vc(__comp), typename __base::allocator_type(__a))
20390b57cec5SDimitry Andric        {
20400b57cec5SDimitry Andric            insert(__il.begin(), __il.end());
20410b57cec5SDimitry Andric        }
20420b57cec5SDimitry Andric
204306c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
2044*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20450b57cec5SDimitry Andric    multimap(initializer_list<value_type> __il, const allocator_type& __a)
20460b57cec5SDimitry Andric        : multimap(__il, key_compare(), __a) {}
20470b57cec5SDimitry Andric#endif
20480b57cec5SDimitry Andric
2049*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20500b57cec5SDimitry Andric    multimap& operator=(initializer_list<value_type> __il)
20510b57cec5SDimitry Andric        {
20520b57cec5SDimitry Andric            __tree_.__assign_multi(__il.begin(), __il.end());
20530b57cec5SDimitry Andric            return *this;
20540b57cec5SDimitry Andric        }
20550b57cec5SDimitry Andric
20560b57cec5SDimitry Andric#endif // _LIBCPP_CXX03_LANG
20570b57cec5SDimitry Andric
2058*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20590b57cec5SDimitry Andric    explicit multimap(const allocator_type& __a)
20600b57cec5SDimitry Andric        : __tree_(typename __base::allocator_type(__a))
20610b57cec5SDimitry Andric        {
20620b57cec5SDimitry Andric        }
20630b57cec5SDimitry Andric
2064*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20650b57cec5SDimitry Andric    multimap(const multimap& __m, const allocator_type& __a)
20660b57cec5SDimitry Andric        : __tree_(__m.__tree_.value_comp(), typename __base::allocator_type(__a))
20670b57cec5SDimitry Andric        {
20680b57cec5SDimitry Andric            insert(__m.begin(), __m.end());
20690b57cec5SDimitry Andric        }
20700b57cec5SDimitry Andric
2071*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20720b57cec5SDimitry Andric    ~multimap() {
20730b57cec5SDimitry Andric        static_assert(sizeof(__diagnose_non_const_comparator<_Key, _Compare>()), "");
20740b57cec5SDimitry Andric    }
20750b57cec5SDimitry Andric
2076*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20770b57cec5SDimitry Andric          iterator begin() _NOEXCEPT {return __tree_.begin();}
2078*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20790b57cec5SDimitry Andric    const_iterator begin() const _NOEXCEPT {return __tree_.begin();}
2080*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20810b57cec5SDimitry Andric          iterator end() _NOEXCEPT {return __tree_.end();}
2082*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20830b57cec5SDimitry Andric    const_iterator end() const _NOEXCEPT {return __tree_.end();}
20840b57cec5SDimitry Andric
2085*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20860b57cec5SDimitry Andric          reverse_iterator rbegin() _NOEXCEPT {return reverse_iterator(end());}
2087*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20880b57cec5SDimitry Andric    const_reverse_iterator rbegin() const _NOEXCEPT
20890b57cec5SDimitry Andric        {return const_reverse_iterator(end());}
2090*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20910b57cec5SDimitry Andric          reverse_iterator rend() _NOEXCEPT {return reverse_iterator(begin());}
2092*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20930b57cec5SDimitry Andric    const_reverse_iterator rend() const _NOEXCEPT
20940b57cec5SDimitry Andric        {return const_reverse_iterator(begin());}
20950b57cec5SDimitry Andric
2096*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20970b57cec5SDimitry Andric    const_iterator cbegin()  const _NOEXCEPT {return begin();}
2098*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
20990b57cec5SDimitry Andric    const_iterator cend() const _NOEXCEPT {return end();}
2100*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21010b57cec5SDimitry Andric    const_reverse_iterator crbegin() const _NOEXCEPT {return rbegin();}
2102*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21030b57cec5SDimitry Andric    const_reverse_iterator crend() const _NOEXCEPT {return rend();}
21040b57cec5SDimitry Andric
2105*5f757f3fSDimitry Andric    _LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_HIDE_FROM_ABI
21060b57cec5SDimitry Andric    bool empty() const _NOEXCEPT {return __tree_.size() == 0;}
2107*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21080b57cec5SDimitry Andric    size_type size() const _NOEXCEPT {return __tree_.size();}
2109*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21100b57cec5SDimitry Andric    size_type max_size() const _NOEXCEPT {return __tree_.max_size();}
21110b57cec5SDimitry Andric
2112*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21130b57cec5SDimitry Andric    allocator_type get_allocator() const _NOEXCEPT {return allocator_type(__tree_.__alloc());}
2114*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21150b57cec5SDimitry Andric    key_compare    key_comp() const {return __tree_.value_comp().key_comp();}
2116*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21170b57cec5SDimitry Andric    value_compare  value_comp() const
21180b57cec5SDimitry Andric        {return value_compare(__tree_.value_comp().key_comp());}
21190b57cec5SDimitry Andric
21200b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG
21210b57cec5SDimitry Andric
21220b57cec5SDimitry Andric    template <class ..._Args>
2123*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21240b57cec5SDimitry Andric    iterator emplace(_Args&& ...__args) {
2125*5f757f3fSDimitry Andric        return __tree_.__emplace_multi(std::forward<_Args>(__args)...);
21260b57cec5SDimitry Andric    }
21270b57cec5SDimitry Andric
21280b57cec5SDimitry Andric    template <class ..._Args>
2129*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21300b57cec5SDimitry Andric    iterator emplace_hint(const_iterator __p, _Args&& ...__args) {
2131*5f757f3fSDimitry Andric        return __tree_.__emplace_hint_multi(__p.__i_, std::forward<_Args>(__args)...);
21320b57cec5SDimitry Andric    }
21330b57cec5SDimitry Andric
21340b57cec5SDimitry Andric    template <class _Pp,
2135753f127fSDimitry Andric              class = __enable_if_t<is_constructible<value_type, _Pp>::value>>
2136*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
21370b57cec5SDimitry Andric        iterator insert(_Pp&& __p)
2138*5f757f3fSDimitry Andric            {return __tree_.__insert_multi(std::forward<_Pp>(__p));}
21390b57cec5SDimitry Andric
21400b57cec5SDimitry Andric    template <class _Pp,
2141753f127fSDimitry Andric              class = __enable_if_t<is_constructible<value_type, _Pp>::value>>
2142*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
21430b57cec5SDimitry Andric        iterator insert(const_iterator __pos, _Pp&& __p)
2144*5f757f3fSDimitry Andric            {return __tree_.__insert_multi(__pos.__i_, std::forward<_Pp>(__p));}
21450b57cec5SDimitry Andric
2146*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21470b57cec5SDimitry Andric    iterator insert(value_type&& __v)
2148*5f757f3fSDimitry Andric        {return __tree_.__insert_multi(std::move(__v));}
21490b57cec5SDimitry Andric
2150*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21510b57cec5SDimitry Andric    iterator insert(const_iterator __p, value_type&& __v)
2152*5f757f3fSDimitry Andric        {return __tree_.__insert_multi(__p.__i_, std::move(__v));}
21530b57cec5SDimitry Andric
21540b57cec5SDimitry Andric
2155*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21560b57cec5SDimitry Andric    void insert(initializer_list<value_type> __il)
21570b57cec5SDimitry Andric        {insert(__il.begin(), __il.end());}
21580b57cec5SDimitry Andric
21590b57cec5SDimitry Andric#endif // _LIBCPP_CXX03_LANG
21600b57cec5SDimitry Andric
2161*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21620b57cec5SDimitry Andric    iterator insert(const value_type& __v) {return __tree_.__insert_multi(__v);}
21630b57cec5SDimitry Andric
2164*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21650b57cec5SDimitry Andric    iterator insert(const_iterator __p, const value_type& __v)
21660b57cec5SDimitry Andric            {return __tree_.__insert_multi(__p.__i_, __v);}
21670b57cec5SDimitry Andric
21680b57cec5SDimitry Andric    template <class _InputIterator>
2169*5f757f3fSDimitry Andric        _LIBCPP_HIDE_FROM_ABI
21700b57cec5SDimitry Andric        void insert(_InputIterator __f, _InputIterator __l)
21710b57cec5SDimitry Andric        {
21720b57cec5SDimitry Andric            for (const_iterator __e = cend(); __f != __l; ++__f)
21730b57cec5SDimitry Andric                __tree_.__insert_multi(__e.__i_, *__f);
21740b57cec5SDimitry Andric        }
21750b57cec5SDimitry Andric
217606c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 23
217706c3fb27SDimitry Andric    template <_ContainerCompatibleRange<value_type> _Range>
217806c3fb27SDimitry Andric    _LIBCPP_HIDE_FROM_ABI
217906c3fb27SDimitry Andric    void insert_range(_Range&& __range) {
218006c3fb27SDimitry Andric      const_iterator __end = cend();
218106c3fb27SDimitry Andric      for (auto&& __element : __range) {
218206c3fb27SDimitry Andric        __tree_.__insert_multi(__end.__i_, std::forward<decltype(__element)>(__element));
218306c3fb27SDimitry Andric      }
218406c3fb27SDimitry Andric    }
218506c3fb27SDimitry Andric#endif
218606c3fb27SDimitry Andric
2187*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21880b57cec5SDimitry Andric    iterator erase(const_iterator __p) {return __tree_.erase(__p.__i_);}
2189*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21900b57cec5SDimitry Andric    iterator erase(iterator __p)       {return __tree_.erase(__p.__i_);}
2191*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21920b57cec5SDimitry Andric    size_type erase(const key_type& __k) {return __tree_.__erase_multi(__k);}
2193*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21940b57cec5SDimitry Andric    iterator  erase(const_iterator __f, const_iterator __l)
21950b57cec5SDimitry Andric        {return __tree_.erase(__f.__i_, __l.__i_);}
21960b57cec5SDimitry Andric
219706c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 17
2198*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
21990b57cec5SDimitry Andric    iterator insert(node_type&& __nh)
22000b57cec5SDimitry Andric    {
220106c3fb27SDimitry Andric        _LIBCPP_ASSERT_COMPATIBLE_ALLOCATOR(__nh.empty() || __nh.get_allocator() == get_allocator(),
22020b57cec5SDimitry Andric            "node_type with incompatible allocator passed to multimap::insert()");
22030b57cec5SDimitry Andric        return __tree_.template __node_handle_insert_multi<node_type>(
2204*5f757f3fSDimitry Andric            std::move(__nh));
22050b57cec5SDimitry Andric    }
2206*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
22070b57cec5SDimitry Andric    iterator insert(const_iterator __hint, node_type&& __nh)
22080b57cec5SDimitry Andric    {
220906c3fb27SDimitry Andric        _LIBCPP_ASSERT_COMPATIBLE_ALLOCATOR(__nh.empty() || __nh.get_allocator() == get_allocator(),
22100b57cec5SDimitry Andric            "node_type with incompatible allocator passed to multimap::insert()");
22110b57cec5SDimitry Andric        return __tree_.template __node_handle_insert_multi<node_type>(
2212*5f757f3fSDimitry Andric            __hint.__i_, std::move(__nh));
22130b57cec5SDimitry Andric    }
2214*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
22150b57cec5SDimitry Andric    node_type extract(key_type const& __key)
22160b57cec5SDimitry Andric    {
22170b57cec5SDimitry Andric        return __tree_.template __node_handle_extract<node_type>(__key);
22180b57cec5SDimitry Andric    }
2219*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
22200b57cec5SDimitry Andric    node_type extract(const_iterator __it)
22210b57cec5SDimitry Andric    {
22220b57cec5SDimitry Andric        return __tree_.template __node_handle_extract<node_type>(
22230b57cec5SDimitry Andric            __it.__i_);
22240b57cec5SDimitry Andric    }
22250b57cec5SDimitry Andric    template <class _Compare2>
2226*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
22270b57cec5SDimitry Andric    void merge(multimap<key_type, mapped_type, _Compare2, allocator_type>& __source)
22280b57cec5SDimitry Andric    {
222906c3fb27SDimitry Andric        _LIBCPP_ASSERT_COMPATIBLE_ALLOCATOR(__source.get_allocator() == get_allocator(),
22300b57cec5SDimitry Andric                                            "merging container with incompatible allocator");
22310b57cec5SDimitry Andric        return __tree_.__node_handle_merge_multi(__source.__tree_);
22320b57cec5SDimitry Andric    }
22330b57cec5SDimitry Andric    template <class _Compare2>
2234*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
22350b57cec5SDimitry Andric    void merge(multimap<key_type, mapped_type, _Compare2, allocator_type>&& __source)
22360b57cec5SDimitry Andric    {
223706c3fb27SDimitry Andric        _LIBCPP_ASSERT_COMPATIBLE_ALLOCATOR(__source.get_allocator() == get_allocator(),
22380b57cec5SDimitry Andric                                            "merging container with incompatible allocator");
22390b57cec5SDimitry Andric        return __tree_.__node_handle_merge_multi(__source.__tree_);
22400b57cec5SDimitry Andric    }
22410b57cec5SDimitry Andric    template <class _Compare2>
2242*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
22430b57cec5SDimitry Andric    void merge(map<key_type, mapped_type, _Compare2, allocator_type>& __source)
22440b57cec5SDimitry Andric    {
224506c3fb27SDimitry Andric        _LIBCPP_ASSERT_COMPATIBLE_ALLOCATOR(__source.get_allocator() == get_allocator(),
22460b57cec5SDimitry Andric                                            "merging container with incompatible allocator");
22470b57cec5SDimitry Andric        return __tree_.__node_handle_merge_multi(__source.__tree_);
22480b57cec5SDimitry Andric    }
22490b57cec5SDimitry Andric    template <class _Compare2>
2250*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
22510b57cec5SDimitry Andric    void merge(map<key_type, mapped_type, _Compare2, allocator_type>&& __source)
22520b57cec5SDimitry Andric    {
225306c3fb27SDimitry Andric        _LIBCPP_ASSERT_COMPATIBLE_ALLOCATOR(__source.get_allocator() == get_allocator(),
22540b57cec5SDimitry Andric                                            "merging container with incompatible allocator");
22550b57cec5SDimitry Andric        return __tree_.__node_handle_merge_multi(__source.__tree_);
22560b57cec5SDimitry Andric    }
22570b57cec5SDimitry Andric#endif
22580b57cec5SDimitry Andric
2259*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
22600b57cec5SDimitry Andric    void clear() _NOEXCEPT {__tree_.clear();}
22610b57cec5SDimitry Andric
2262*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
22630b57cec5SDimitry Andric    void swap(multimap& __m)
22640b57cec5SDimitry Andric        _NOEXCEPT_(__is_nothrow_swappable<__base>::value)
22650b57cec5SDimitry Andric        {__tree_.swap(__m.__tree_);}
22660b57cec5SDimitry Andric
2267*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
22680b57cec5SDimitry Andric    iterator find(const key_type& __k)             {return __tree_.find(__k);}
2269*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
22700b57cec5SDimitry Andric    const_iterator find(const key_type& __k) const {return __tree_.find(__k);}
227106c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
2272*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
2273*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
2274*5f757f3fSDimitry Andric    iterator
22750b57cec5SDimitry Andric    find(const _K2& __k)                           {return __tree_.find(__k);}
2276*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
2277*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
2278*5f757f3fSDimitry Andric    const_iterator
22790b57cec5SDimitry Andric    find(const _K2& __k) const                     {return __tree_.find(__k);}
22800b57cec5SDimitry Andric#endif
22810b57cec5SDimitry Andric
2282*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
22830b57cec5SDimitry Andric    size_type      count(const key_type& __k) const
22840b57cec5SDimitry Andric        {return __tree_.__count_multi(__k);}
228506c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
2286*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
2287*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
2288*5f757f3fSDimitry Andric    size_type
22890b57cec5SDimitry Andric    count(const _K2& __k) const {return __tree_.__count_multi(__k);}
22900b57cec5SDimitry Andric#endif
22910b57cec5SDimitry Andric
229206c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 20
2293*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
22940b57cec5SDimitry Andric    bool contains(const key_type& __k) const {return find(__k) != end();}
2295*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
2296*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
2297*5f757f3fSDimitry Andric    bool
2298fe6060f1SDimitry Andric    contains(const _K2& __k) const { return find(__k) != end(); }
229906c3fb27SDimitry Andric#endif // _LIBCPP_STD_VER >= 20
23000b57cec5SDimitry Andric
2301*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
23020b57cec5SDimitry Andric    iterator lower_bound(const key_type& __k)
23030b57cec5SDimitry Andric        {return __tree_.lower_bound(__k);}
2304*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
23050b57cec5SDimitry Andric    const_iterator lower_bound(const key_type& __k) const
23060b57cec5SDimitry Andric            {return __tree_.lower_bound(__k);}
230706c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
2308*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
2309*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
2310*5f757f3fSDimitry Andric    iterator
23110b57cec5SDimitry Andric    lower_bound(const _K2& __k)       {return __tree_.lower_bound(__k);}
23120b57cec5SDimitry Andric
2313*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
2314*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
2315*5f757f3fSDimitry Andric    const_iterator
23160b57cec5SDimitry Andric    lower_bound(const _K2& __k) const {return __tree_.lower_bound(__k);}
23170b57cec5SDimitry Andric#endif
23180b57cec5SDimitry Andric
2319*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
23200b57cec5SDimitry Andric    iterator upper_bound(const key_type& __k)
23210b57cec5SDimitry Andric            {return __tree_.upper_bound(__k);}
2322*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
23230b57cec5SDimitry Andric    const_iterator upper_bound(const key_type& __k) const
23240b57cec5SDimitry Andric            {return __tree_.upper_bound(__k);}
232506c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
2326*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
2327*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
2328*5f757f3fSDimitry Andric    iterator
23290b57cec5SDimitry Andric    upper_bound(const _K2& __k)       {return __tree_.upper_bound(__k);}
2330*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
2331*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
2332*5f757f3fSDimitry Andric    const_iterator
23330b57cec5SDimitry Andric    upper_bound(const _K2& __k) const {return __tree_.upper_bound(__k);}
23340b57cec5SDimitry Andric#endif
23350b57cec5SDimitry Andric
2336*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
23370b57cec5SDimitry Andric    pair<iterator,iterator>             equal_range(const key_type& __k)
23380b57cec5SDimitry Andric            {return __tree_.__equal_range_multi(__k);}
2339*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
23400b57cec5SDimitry Andric    pair<const_iterator,const_iterator> equal_range(const key_type& __k) const
23410b57cec5SDimitry Andric            {return __tree_.__equal_range_multi(__k);}
234206c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 14
2343*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
2344*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
2345*5f757f3fSDimitry Andric    pair<iterator,iterator>
23460b57cec5SDimitry Andric    equal_range(const _K2& __k)       {return __tree_.__equal_range_multi(__k);}
2347*5f757f3fSDimitry Andric    template <typename _K2, enable_if_t<__is_transparent<_Compare, _K2>::value, int> = 0>
2348*5f757f3fSDimitry Andric    _LIBCPP_HIDE_FROM_ABI
2349*5f757f3fSDimitry Andric    pair<const_iterator,const_iterator>
23500b57cec5SDimitry Andric    equal_range(const _K2& __k) const {return __tree_.__equal_range_multi(__k);}
23510b57cec5SDimitry Andric#endif
23520b57cec5SDimitry Andric
23530b57cec5SDimitry Andricprivate:
23540b57cec5SDimitry Andric    typedef typename __base::__node                    __node;
23550b57cec5SDimitry Andric    typedef typename __base::__node_allocator          __node_allocator;
23560b57cec5SDimitry Andric    typedef typename __base::__node_pointer            __node_pointer;
23570b57cec5SDimitry Andric
23580b57cec5SDimitry Andric    typedef __map_node_destructor<__node_allocator> _Dp;
23590b57cec5SDimitry Andric    typedef unique_ptr<__node, _Dp> __node_holder;
23600b57cec5SDimitry Andric};
23610b57cec5SDimitry Andric
2362349cc55cSDimitry Andric#if _LIBCPP_STD_VER >= 17
23630b57cec5SDimitry Andrictemplate<class _InputIterator, class _Compare = less<__iter_key_type<_InputIterator>>,
23640b57cec5SDimitry Andric         class _Allocator = allocator<__iter_to_alloc_type<_InputIterator>>,
236506c3fb27SDimitry Andric         class = enable_if_t<__has_input_iterator_category<_InputIterator>::value, void>,
2366349cc55cSDimitry Andric         class = enable_if_t<!__is_allocator<_Compare>::value, void>,
2367349cc55cSDimitry Andric         class = enable_if_t<__is_allocator<_Allocator>::value, void>>
23680b57cec5SDimitry Andricmultimap(_InputIterator, _InputIterator, _Compare = _Compare(), _Allocator = _Allocator())
23690b57cec5SDimitry Andric  -> multimap<__iter_key_type<_InputIterator>, __iter_mapped_type<_InputIterator>, _Compare, _Allocator>;
23700b57cec5SDimitry Andric
237106c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 23
237206c3fb27SDimitry Andrictemplate <ranges::input_range _Range, class _Compare = less<__range_key_type<_Range>>,
237306c3fb27SDimitry Andric          class _Allocator = allocator<__range_to_alloc_type<_Range>>,
237406c3fb27SDimitry Andric          class = enable_if_t<!__is_allocator<_Compare>::value, void>,
237506c3fb27SDimitry Andric          class = enable_if_t<__is_allocator<_Allocator>::value, void>>
237606c3fb27SDimitry Andricmultimap(from_range_t, _Range&&, _Compare = _Compare(), _Allocator = _Allocator())
237706c3fb27SDimitry Andric  -> multimap<__range_key_type<_Range>, __range_mapped_type<_Range>, _Compare, _Allocator>;
237806c3fb27SDimitry Andric#endif
237906c3fb27SDimitry Andric
23800b57cec5SDimitry Andrictemplate<class _Key, class _Tp, class _Compare = less<remove_const_t<_Key>>,
23810b57cec5SDimitry Andric         class _Allocator = allocator<pair<const _Key, _Tp>>,
2382349cc55cSDimitry Andric         class = enable_if_t<!__is_allocator<_Compare>::value, void>,
2383349cc55cSDimitry Andric         class = enable_if_t<__is_allocator<_Allocator>::value, void>>
23840b57cec5SDimitry Andricmultimap(initializer_list<pair<_Key, _Tp>>, _Compare = _Compare(), _Allocator = _Allocator())
23850b57cec5SDimitry Andric  -> multimap<remove_const_t<_Key>, _Tp, _Compare, _Allocator>;
23860b57cec5SDimitry Andric
23870b57cec5SDimitry Andrictemplate<class _InputIterator, class _Allocator,
238806c3fb27SDimitry Andric         class = enable_if_t<__has_input_iterator_category<_InputIterator>::value, void>,
2389349cc55cSDimitry Andric         class = enable_if_t<__is_allocator<_Allocator>::value, void>>
23900b57cec5SDimitry Andricmultimap(_InputIterator, _InputIterator, _Allocator)
23910b57cec5SDimitry Andric  -> multimap<__iter_key_type<_InputIterator>, __iter_mapped_type<_InputIterator>,
23920b57cec5SDimitry Andric         less<__iter_key_type<_InputIterator>>, _Allocator>;
23930b57cec5SDimitry Andric
239406c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 23
239506c3fb27SDimitry Andrictemplate <ranges::input_range _Range, class _Allocator,
239606c3fb27SDimitry Andric          class = enable_if_t<__is_allocator<_Allocator>::value, void>>
239706c3fb27SDimitry Andricmultimap(from_range_t, _Range&&, _Allocator)
239806c3fb27SDimitry Andric  -> multimap<__range_key_type<_Range>, __range_mapped_type<_Range>, less<__range_key_type<_Range>>, _Allocator>;
239906c3fb27SDimitry Andric#endif
240006c3fb27SDimitry Andric
24010b57cec5SDimitry Andrictemplate<class _Key, class _Tp, class _Allocator,
2402349cc55cSDimitry Andric         class = enable_if_t<__is_allocator<_Allocator>::value, void>>
24030b57cec5SDimitry Andricmultimap(initializer_list<pair<_Key, _Tp>>, _Allocator)
24040b57cec5SDimitry Andric  -> multimap<remove_const_t<_Key>, _Tp, less<remove_const_t<_Key>>, _Allocator>;
24050b57cec5SDimitry Andric#endif
24060b57cec5SDimitry Andric
24070b57cec5SDimitry Andric#ifndef _LIBCPP_CXX03_LANG
24080b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
24090b57cec5SDimitry Andricmultimap<_Key, _Tp, _Compare, _Allocator>::multimap(multimap&& __m, const allocator_type& __a)
2410*5f757f3fSDimitry Andric    : __tree_(std::move(__m.__tree_), typename __base::allocator_type(__a))
24110b57cec5SDimitry Andric{
24120b57cec5SDimitry Andric    if (__a != __m.get_allocator())
24130b57cec5SDimitry Andric    {
24140b57cec5SDimitry Andric        const_iterator __e = cend();
24150b57cec5SDimitry Andric        while (!__m.empty())
24160b57cec5SDimitry Andric            __tree_.__insert_multi(__e.__i_,
2417*5f757f3fSDimitry Andric                    std::move(__m.__tree_.remove(__m.begin().__i_)->__value_.__move()));
24180b57cec5SDimitry Andric    }
24190b57cec5SDimitry Andric}
24200b57cec5SDimitry Andric#endif
24210b57cec5SDimitry Andric
24220b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
2423*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
24240b57cec5SDimitry Andricbool
24250b57cec5SDimitry Andricoperator==(const multimap<_Key, _Tp, _Compare, _Allocator>& __x,
24260b57cec5SDimitry Andric           const multimap<_Key, _Tp, _Compare, _Allocator>& __y)
24270b57cec5SDimitry Andric{
2428*5f757f3fSDimitry Andric    return __x.size() == __y.size() && std::equal(__x.begin(), __x.end(), __y.begin());
24290b57cec5SDimitry Andric}
24300b57cec5SDimitry Andric
243106c3fb27SDimitry Andric#if _LIBCPP_STD_VER <= 17
243206c3fb27SDimitry Andric
24330b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
2434*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
24350b57cec5SDimitry Andricbool
24360b57cec5SDimitry Andricoperator< (const multimap<_Key, _Tp, _Compare, _Allocator>& __x,
24370b57cec5SDimitry Andric           const multimap<_Key, _Tp, _Compare, _Allocator>& __y)
24380b57cec5SDimitry Andric{
2439*5f757f3fSDimitry Andric    return std::lexicographical_compare(__x.begin(), __x.end(), __y.begin(), __y.end());
24400b57cec5SDimitry Andric}
24410b57cec5SDimitry Andric
24420b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
2443*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
24440b57cec5SDimitry Andricbool
24450b57cec5SDimitry Andricoperator!=(const multimap<_Key, _Tp, _Compare, _Allocator>& __x,
24460b57cec5SDimitry Andric           const multimap<_Key, _Tp, _Compare, _Allocator>& __y)
24470b57cec5SDimitry Andric{
24480b57cec5SDimitry Andric    return !(__x == __y);
24490b57cec5SDimitry Andric}
24500b57cec5SDimitry Andric
24510b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
2452*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
24530b57cec5SDimitry Andricbool
24540b57cec5SDimitry Andricoperator> (const multimap<_Key, _Tp, _Compare, _Allocator>& __x,
24550b57cec5SDimitry Andric           const multimap<_Key, _Tp, _Compare, _Allocator>& __y)
24560b57cec5SDimitry Andric{
24570b57cec5SDimitry Andric    return __y < __x;
24580b57cec5SDimitry Andric}
24590b57cec5SDimitry Andric
24600b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
2461*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
24620b57cec5SDimitry Andricbool
24630b57cec5SDimitry Andricoperator>=(const multimap<_Key, _Tp, _Compare, _Allocator>& __x,
24640b57cec5SDimitry Andric           const multimap<_Key, _Tp, _Compare, _Allocator>& __y)
24650b57cec5SDimitry Andric{
24660b57cec5SDimitry Andric    return !(__x < __y);
24670b57cec5SDimitry Andric}
24680b57cec5SDimitry Andric
24690b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
2470*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
24710b57cec5SDimitry Andricbool
24720b57cec5SDimitry Andricoperator<=(const multimap<_Key, _Tp, _Compare, _Allocator>& __x,
24730b57cec5SDimitry Andric           const multimap<_Key, _Tp, _Compare, _Allocator>& __y)
24740b57cec5SDimitry Andric{
24750b57cec5SDimitry Andric    return !(__y < __x);
24760b57cec5SDimitry Andric}
24770b57cec5SDimitry Andric
247806c3fb27SDimitry Andric#else // #if _LIBCPP_STD_VER <= 17
247906c3fb27SDimitry Andric
248006c3fb27SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
248106c3fb27SDimitry Andric_LIBCPP_HIDE_FROM_ABI __synth_three_way_result<pair<const _Key, _Tp>>
248206c3fb27SDimitry Andricoperator<=>(const multimap<_Key, _Tp, _Compare, _Allocator>& __x,
248306c3fb27SDimitry Andric            const multimap<_Key, _Tp, _Compare, _Allocator>& __y) {
248406c3fb27SDimitry Andric    return std::lexicographical_compare_three_way(
248506c3fb27SDimitry Andric        __x.begin(),
248606c3fb27SDimitry Andric        __x.end(),
248706c3fb27SDimitry Andric        __y.begin(),
248806c3fb27SDimitry Andric        __y.end(),
248906c3fb27SDimitry Andric        std::__synth_three_way<pair<const _Key, _Tp>, pair<const _Key, _Tp>>);
249006c3fb27SDimitry Andric}
249106c3fb27SDimitry Andric
249206c3fb27SDimitry Andric#endif // #if _LIBCPP_STD_VER <= 17
249306c3fb27SDimitry Andric
24940b57cec5SDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator>
2495*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
24960b57cec5SDimitry Andricvoid
24970b57cec5SDimitry Andricswap(multimap<_Key, _Tp, _Compare, _Allocator>& __x,
24980b57cec5SDimitry Andric     multimap<_Key, _Tp, _Compare, _Allocator>& __y)
24990b57cec5SDimitry Andric    _NOEXCEPT_(_NOEXCEPT_(__x.swap(__y)))
25000b57cec5SDimitry Andric{
25010b57cec5SDimitry Andric    __x.swap(__y);
25020b57cec5SDimitry Andric}
25030b57cec5SDimitry Andric
250406c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 20
25055ffd83dbSDimitry Andrictemplate <class _Key, class _Tp, class _Compare, class _Allocator,
25065ffd83dbSDimitry Andric          class _Predicate>
2507*5f757f3fSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI
25085ffd83dbSDimitry Andric    typename multimap<_Key, _Tp, _Compare, _Allocator>::size_type
25095ffd83dbSDimitry Andric    erase_if(multimap<_Key, _Tp, _Compare, _Allocator>& __c,
25105ffd83dbSDimitry Andric             _Predicate __pred) {
2511*5f757f3fSDimitry Andric  return std::__libcpp_erase_if_container(__c, __pred);
25125ffd83dbSDimitry Andric}
25130b57cec5SDimitry Andric#endif
25140b57cec5SDimitry Andric
25150b57cec5SDimitry Andric_LIBCPP_END_NAMESPACE_STD
25160b57cec5SDimitry Andric
251706c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 17
2518bdd1243dSDimitry Andric_LIBCPP_BEGIN_NAMESPACE_STD
2519bdd1243dSDimitry Andricnamespace pmr {
2520bdd1243dSDimitry Andrictemplate <class _KeyT, class _ValueT, class _CompareT = std::less<_KeyT>>
252106c3fb27SDimitry Andricusing map _LIBCPP_AVAILABILITY_PMR = std::map<_KeyT, _ValueT, _CompareT, polymorphic_allocator<std::pair<const _KeyT, _ValueT>>>;
2522bdd1243dSDimitry Andric
2523bdd1243dSDimitry Andrictemplate <class _KeyT, class _ValueT, class _CompareT = std::less<_KeyT>>
252406c3fb27SDimitry Andricusing multimap _LIBCPP_AVAILABILITY_PMR = std::multimap<_KeyT, _ValueT, _CompareT, polymorphic_allocator<std::pair<const _KeyT, _ValueT>>>;
2525bdd1243dSDimitry Andric} // namespace pmr
2526bdd1243dSDimitry Andric_LIBCPP_END_NAMESPACE_STD
2527bdd1243dSDimitry Andric#endif
2528bdd1243dSDimitry Andric
2529bdd1243dSDimitry Andric#if !defined(_LIBCPP_REMOVE_TRANSITIVE_INCLUDES) && _LIBCPP_STD_VER <= 20
2530bdd1243dSDimitry Andric#  include <concepts>
253106c3fb27SDimitry Andric#  include <cstdlib>
2532bdd1243dSDimitry Andric#  include <functional>
2533bdd1243dSDimitry Andric#  include <iterator>
253406c3fb27SDimitry Andric#  include <type_traits>
2535bdd1243dSDimitry Andric#  include <utility>
2536bdd1243dSDimitry Andric#endif
2537bdd1243dSDimitry Andric
25380b57cec5SDimitry Andric#endif // _LIBCPP_MAP
2539