1// -*- C++ -*-
2//===-------------------------- iterator ----------------------------------===//
3//
4// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
5// See https://llvm.org/LICENSE.txt for license information.
6// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7//
8//===----------------------------------------------------------------------===//
9
10#ifndef _LIBCPP_ITERATOR
11#define _LIBCPP_ITERATOR
12
13/*
14    iterator synopsis
15
16#include <concepts>
17
18namespace std
19{
20template<class> struct incrementable_traits;       // since C++20
21template<class T>
22  using iter_difference_t = see below;             // since C++20
23
24template<class> struct indirectly_readable_traits; // since C++20
25template<class T>
26  using iter_value_t = see below;                  // since C++20
27
28template<class Iterator>
29struct iterator_traits;
30
31template<class T>
32  requires is_object_v<T>                    // since C++20
33struct iterator_traits<T*>;
34
35template<dereferenceable T>
36  using iter_reference_t = decltype(*declval<T&>());
37
38namespace ranges::inline unspecified {
39    inline constexpr unspecified iter_move = unspecified; // since C++20, nodiscard as an extension
40}}
41
42template<dereferenceable T>
43  requires ...
44using iter_rvalue_reference_t = decltype(ranges::iter_move(declval<T&>())); // since C++20
45
46// [iterator.concepts], iterator concepts
47// [iterator.concept.readable], concept indirectly_readable
48template<class In>
49  concept indirectly_readable = see below;                // since C++20
50
51// [iterator.concept.writable], concept indirectly_writable
52template<class Out, class T>
53  concept indirectly_writable = see below;                // since C++20
54
55// [iterator.concept.winc], concept weakly_incrementable
56template<class I>
57  concept weakly_incrementable = see below;                // since C++20
58
59// [iterator.concept.inc], concept incrementable
60template<class I>
61  concept incrementable = see below;                       // since C++20
62
63// [iterator.concept.iterator], concept input_or_output_iterator
64  template<class I>
65    concept input_or_output_iterator = see below;          // since C++20
66
67// [iterator.concept.sentinel], concept sentinel_for
68template<class S, class I>
69  concept sentinel_for = see below;                        // since C++20
70
71// [iterator.concept.sizedsentinel], concept sized_sentinel_for
72template<class S, class I>
73  inline constexpr bool disable_sized_sentinel_for = false;
74
75template<class S, class I>
76  concept sized_sentinel_for = see below;
77
78template<class Category, class T, class Distance = ptrdiff_t,
79         class Pointer = T*, class Reference = T&>
80struct iterator
81{
82    typedef T         value_type;
83    typedef Distance  difference_type;
84    typedef Pointer   pointer;
85    typedef Reference reference;
86    typedef Category  iterator_category;
87};
88
89struct input_iterator_tag  {};
90struct output_iterator_tag {};
91struct forward_iterator_tag       : public input_iterator_tag         {};
92struct bidirectional_iterator_tag : public forward_iterator_tag       {};
93struct random_access_iterator_tag : public bidirectional_iterator_tag {};
94
95// 27.4.3, iterator operations
96template <class InputIterator, class Distance>  // constexpr in C++17
97  constexpr void advance(InputIterator& i, Distance n);
98
99template <class InputIterator>  // constexpr in C++17
100  constexpr typename iterator_traits<InputIterator>::difference_type
101    distance(InputIterator first, InputIterator last);
102
103template <class InputIterator>  // constexpr in C++17
104  constexpr InputIterator next(InputIterator x,
105typename iterator_traits<InputIterator>::difference_type n = 1);
106
107template <class BidirectionalIterator>  // constexpr in C++17
108  constexpr BidirectionalIterator prev(BidirectionalIterator x,
109    typename iterator_traits<BidirectionalIterator>::difference_type n = 1);
110
111template <class Iterator>
112class reverse_iterator
113    : public iterator<typename iterator_traits<Iterator>::iterator_category,
114                      typename iterator_traits<Iterator>::value_type,
115                      typename iterator_traits<Iterator>::difference_type,
116                      typename iterator_traits<Iterator>::pointer,
117                      typename iterator_traits<Iterator>::reference>
118{
119protected:
120    Iterator current;
121public:
122    typedef Iterator                                            iterator_type;
123    typedef typename iterator_traits<Iterator>::difference_type difference_type;
124    typedef typename iterator_traits<Iterator>::reference       reference;
125    typedef typename iterator_traits<Iterator>::pointer         pointer;
126
127    constexpr reverse_iterator();
128    constexpr explicit reverse_iterator(Iterator x);
129    template <class U> constexpr reverse_iterator(const reverse_iterator<U>& u);
130    template <class U> constexpr reverse_iterator& operator=(const reverse_iterator<U>& u);
131    constexpr Iterator base() const;
132    constexpr reference operator*() const;
133    constexpr pointer   operator->() const;
134    constexpr reverse_iterator& operator++();
135    constexpr reverse_iterator  operator++(int);
136    constexpr reverse_iterator& operator--();
137    constexpr reverse_iterator  operator--(int);
138    constexpr reverse_iterator  operator+ (difference_type n) const;
139    constexpr reverse_iterator& operator+=(difference_type n);
140    constexpr reverse_iterator  operator- (difference_type n) const;
141    constexpr reverse_iterator& operator-=(difference_type n);
142    constexpr reference         operator[](difference_type n) const;
143};
144
145template <class Iterator1, class Iterator2>
146constexpr bool                          // constexpr in C++17
147operator==(const reverse_iterator<Iterator1>& x, const reverse_iterator<Iterator2>& y);
148
149template <class Iterator1, class Iterator2>
150constexpr bool                          // constexpr in C++17
151operator<(const reverse_iterator<Iterator1>& x, const reverse_iterator<Iterator2>& y);
152
153template <class Iterator1, class Iterator2>
154constexpr bool                          // constexpr in C++17
155operator!=(const reverse_iterator<Iterator1>& x, const reverse_iterator<Iterator2>& y);
156
157template <class Iterator1, class Iterator2>
158constexpr bool                          // constexpr in C++17
159operator>(const reverse_iterator<Iterator1>& x, const reverse_iterator<Iterator2>& y);
160
161template <class Iterator1, class Iterator2>
162constexpr bool                          // constexpr in C++17
163operator>=(const reverse_iterator<Iterator1>& x, const reverse_iterator<Iterator2>& y);
164
165template <class Iterator1, class Iterator2>
166constexpr bool                          // constexpr in C++17
167operator<=(const reverse_iterator<Iterator1>& x, const reverse_iterator<Iterator2>& y);
168
169template <class Iterator1, class Iterator2>
170constexpr auto
171operator-(const reverse_iterator<Iterator1>& x, const reverse_iterator<Iterator2>& y)
172-> decltype(__y.base() - __x.base());   // constexpr in C++17
173
174template <class Iterator>
175constexpr reverse_iterator<Iterator>
176operator+(typename reverse_iterator<Iterator>::difference_type n,
177          const reverse_iterator<Iterator>& x);   // constexpr in C++17
178
179template <class Iterator>
180constexpr reverse_iterator<Iterator> make_reverse_iterator(Iterator i); // C++14, constexpr in C++17
181
182template <class Container>
183class back_insert_iterator
184{
185protected:
186    Container* container;
187public:
188    typedef Container                   container_type;
189    typedef void                        value_type;
190    typedef void                        difference_type;
191    typedef void                        reference;
192    typedef void                        pointer;
193
194    explicit back_insert_iterator(Container& x);  // constexpr in C++20
195    back_insert_iterator& operator=(const typename Container::value_type& value);  // constexpr in C++20
196    back_insert_iterator& operator*();  // constexpr in C++20
197    back_insert_iterator& operator++();  // constexpr in C++20
198    back_insert_iterator  operator++(int);  // constexpr in C++20
199};
200
201template <class Container> back_insert_iterator<Container> back_inserter(Container& x);  // constexpr in C++20
202
203template <class Container>
204class front_insert_iterator
205{
206protected:
207    Container* container;
208public:
209    typedef Container                    container_type;
210    typedef void                         value_type;
211    typedef void                         difference_type;
212    typedef void                         reference;
213    typedef void                         pointer;
214
215    explicit front_insert_iterator(Container& x);  // constexpr in C++20
216    front_insert_iterator& operator=(const typename Container::value_type& value);  // constexpr in C++20
217    front_insert_iterator& operator*();  // constexpr in C++20
218    front_insert_iterator& operator++();  // constexpr in C++20
219    front_insert_iterator  operator++(int);  // constexpr in C++20
220};
221
222template <class Container> front_insert_iterator<Container> front_inserter(Container& x);  // constexpr in C++20
223
224template <class Container>
225class insert_iterator
226{
227protected:
228    Container* container;
229    typename Container::iterator iter;
230public:
231    typedef Container              container_type;
232    typedef void                   value_type;
233    typedef void                   difference_type;
234    typedef void                   reference;
235    typedef void                   pointer;
236
237    insert_iterator(Container& x, typename Container::iterator i);  // constexpr in C++20
238    insert_iterator& operator=(const typename Container::value_type& value);  // constexpr in C++20
239    insert_iterator& operator*();  // constexpr in C++20
240    insert_iterator& operator++();  // constexpr in C++20
241    insert_iterator& operator++(int);  // constexpr in C++20
242};
243
244template <class Container, class Iterator>
245insert_iterator<Container> inserter(Container& x, Iterator i);  // constexpr in C++20
246
247template <class Iterator>
248class move_iterator {
249public:
250    typedef Iterator                                              iterator_type;
251    typedef typename iterator_traits<Iterator>::difference_type   difference_type;
252    typedef Iterator                                              pointer;
253    typedef typename iterator_traits<Iterator>::value_type        value_type;
254    typedef typename iterator_traits<Iterator>::iterator_category iterator_category;
255    typedef value_type&&                                          reference;
256
257    constexpr move_iterator();  // all the constexprs are in C++17
258    constexpr explicit move_iterator(Iterator i);
259    template <class U>
260      constexpr move_iterator(const move_iterator<U>& u);
261    template <class U>
262      constexpr move_iterator& operator=(const move_iterator<U>& u);
263    constexpr iterator_type base() const;
264    constexpr reference operator*() const;
265    constexpr pointer operator->() const;
266    constexpr move_iterator& operator++();
267    constexpr move_iterator operator++(int);
268    constexpr move_iterator& operator--();
269    constexpr move_iterator operator--(int);
270    constexpr move_iterator operator+(difference_type n) const;
271    constexpr move_iterator& operator+=(difference_type n);
272    constexpr move_iterator operator-(difference_type n) const;
273    constexpr move_iterator& operator-=(difference_type n);
274    constexpr unspecified operator[](difference_type n) const;
275private:
276    Iterator current; // exposition only
277};
278
279template <class Iterator1, class Iterator2>
280constexpr bool   // constexpr in C++17
281operator==(const move_iterator<Iterator1>& x, const move_iterator<Iterator2>& y);
282
283template <class Iterator1, class Iterator2>
284constexpr bool   // constexpr in C++17
285operator!=(const move_iterator<Iterator1>& x, const move_iterator<Iterator2>& y);
286
287template <class Iterator1, class Iterator2>
288constexpr bool   // constexpr in C++17
289operator<(const move_iterator<Iterator1>& x, const move_iterator<Iterator2>& y);
290
291template <class Iterator1, class Iterator2>
292constexpr bool   // constexpr in C++17
293operator<=(const move_iterator<Iterator1>& x, const move_iterator<Iterator2>& y);
294
295template <class Iterator1, class Iterator2>
296constexpr bool   // constexpr in C++17
297operator>(const move_iterator<Iterator1>& x, const move_iterator<Iterator2>& y);
298
299template <class Iterator1, class Iterator2>
300constexpr bool   // constexpr in C++17
301operator>=(const move_iterator<Iterator1>& x, const move_iterator<Iterator2>& y);
302
303template <class Iterator1, class Iterator2>
304constexpr auto   // constexpr in C++17
305operator-(const move_iterator<Iterator1>& x,
306          const move_iterator<Iterator2>& y) -> decltype(x.base() - y.base());
307
308template <class Iterator>
309constexpr move_iterator<Iterator> operator+(   // constexpr in C++17
310            typename move_iterator<Iterator>::difference_type n,
311            const move_iterator<Iterator>& x);
312
313template <class Iterator>   // constexpr in C++17
314constexpr  move_iterator<Iterator> make_move_iterator(const Iterator& i);
315
316
317template <class T, class charT = char, class traits = char_traits<charT>, class Distance = ptrdiff_t>
318class istream_iterator
319    : public iterator<input_iterator_tag, T, Distance, const T*, const T&>
320{
321public:
322    typedef charT char_type;
323    typedef traits traits_type;
324    typedef basic_istream<charT,traits> istream_type;
325
326    constexpr istream_iterator();
327    istream_iterator(istream_type& s);
328    istream_iterator(const istream_iterator& x);
329    ~istream_iterator();
330
331    const T& operator*() const;
332    const T* operator->() const;
333    istream_iterator& operator++();
334    istream_iterator  operator++(int);
335};
336
337template <class T, class charT, class traits, class Distance>
338bool operator==(const istream_iterator<T,charT,traits,Distance>& x,
339                const istream_iterator<T,charT,traits,Distance>& y);
340template <class T, class charT, class traits, class Distance>
341bool operator!=(const istream_iterator<T,charT,traits,Distance>& x,
342                const istream_iterator<T,charT,traits,Distance>& y);
343
344template <class T, class charT = char, class traits = char_traits<charT> >
345class ostream_iterator
346    : public iterator<output_iterator_tag, void, void, void ,void>
347{
348public:
349    typedef charT char_type;
350    typedef traits traits_type;
351    typedef basic_ostream<charT,traits> ostream_type;
352
353    ostream_iterator(ostream_type& s);
354    ostream_iterator(ostream_type& s, const charT* delimiter);
355    ostream_iterator(const ostream_iterator& x);
356    ~ostream_iterator();
357    ostream_iterator& operator=(const T& value);
358
359    ostream_iterator& operator*();
360    ostream_iterator& operator++();
361    ostream_iterator& operator++(int);
362};
363
364template<class charT, class traits = char_traits<charT> >
365class istreambuf_iterator
366    : public iterator<input_iterator_tag, charT,
367                      typename traits::off_type, unspecified,
368                      charT>
369{
370public:
371    typedef charT                         char_type;
372    typedef traits                        traits_type;
373    typedef typename traits::int_type     int_type;
374    typedef basic_streambuf<charT,traits> streambuf_type;
375    typedef basic_istream<charT,traits>   istream_type;
376
377    istreambuf_iterator() noexcept;
378    istreambuf_iterator(istream_type& s) noexcept;
379    istreambuf_iterator(streambuf_type* s) noexcept;
380    istreambuf_iterator(a-private-type) noexcept;
381
382    charT                operator*() const;
383    pointer operator->() const;
384    istreambuf_iterator& operator++();
385    a-private-type       operator++(int);
386
387    bool equal(const istreambuf_iterator& b) const;
388};
389
390template <class charT, class traits>
391bool operator==(const istreambuf_iterator<charT,traits>& a,
392                const istreambuf_iterator<charT,traits>& b);
393template <class charT, class traits>
394bool operator!=(const istreambuf_iterator<charT,traits>& a,
395                const istreambuf_iterator<charT,traits>& b);
396
397template <class charT, class traits = char_traits<charT> >
398class ostreambuf_iterator
399    : public iterator<output_iterator_tag, void, void, void, void>
400{
401public:
402    typedef charT                         char_type;
403    typedef traits                        traits_type;
404    typedef basic_streambuf<charT,traits> streambuf_type;
405    typedef basic_ostream<charT,traits>   ostream_type;
406
407    ostreambuf_iterator(ostream_type& s) noexcept;
408    ostreambuf_iterator(streambuf_type* s) noexcept;
409    ostreambuf_iterator& operator=(charT c);
410    ostreambuf_iterator& operator*();
411    ostreambuf_iterator& operator++();
412    ostreambuf_iterator& operator++(int);
413    bool failed() const noexcept;
414};
415
416template <class C> constexpr auto begin(C& c) -> decltype(c.begin());
417template <class C> constexpr auto begin(const C& c) -> decltype(c.begin());
418template <class C> constexpr auto end(C& c) -> decltype(c.end());
419template <class C> constexpr auto end(const C& c) -> decltype(c.end());
420template <class T, size_t N> constexpr T* begin(T (&array)[N]);
421template <class T, size_t N> constexpr T* end(T (&array)[N]);
422
423template <class C> auto constexpr cbegin(const C& c) -> decltype(std::begin(c));        // C++14
424template <class C> auto constexpr cend(const C& c) -> decltype(std::end(c));            // C++14
425template <class C> auto constexpr rbegin(C& c) -> decltype(c.rbegin());                 // C++14
426template <class C> auto constexpr rbegin(const C& c) -> decltype(c.rbegin());           // C++14
427template <class C> auto constexpr rend(C& c) -> decltype(c.rend());                     // C++14
428template <class C> constexpr auto rend(const C& c) -> decltype(c.rend());               // C++14
429template <class E> reverse_iterator<const E*> constexpr rbegin(initializer_list<E> il); // C++14
430template <class E> reverse_iterator<const E*> constexpr rend(initializer_list<E> il);   // C++14
431template <class T, size_t N> reverse_iterator<T*> constexpr rbegin(T (&array)[N]);      // C++14
432template <class T, size_t N> reverse_iterator<T*> constexpr rend(T (&array)[N]);        // C++14
433template <class C> constexpr auto crbegin(const C& c) -> decltype(std::rbegin(c));      // C++14
434template <class C> constexpr auto crend(const C& c) -> decltype(std::rend(c));          // C++14
435
436// 24.8, container access:
437template <class C> constexpr auto size(const C& c) -> decltype(c.size());         // C++17
438template <class T, size_t N> constexpr size_t size(const T (&array)[N]) noexcept; // C++17
439
440template <class C> constexpr auto ssize(const C& c)
441    -> common_type_t<ptrdiff_t, make_signed_t<decltype(c.size())>>;                    // C++20
442template <class T, ptrdiff_t> constexpr ptrdiff_t ssize(const T (&array)[N]) noexcept; // C++20
443
444template <class C> constexpr auto empty(const C& c) -> decltype(c.empty());       // C++17
445template <class T, size_t N> constexpr bool empty(const T (&array)[N]) noexcept;  // C++17
446template <class E> constexpr bool empty(initializer_list<E> il) noexcept;         // C++17
447template <class C> constexpr auto data(C& c) -> decltype(c.data());               // C++17
448template <class C> constexpr auto data(const C& c) -> decltype(c.data());         // C++17
449template <class T, size_t N> constexpr T* data(T (&array)[N]) noexcept;           // C++17
450template <class E> constexpr const E* data(initializer_list<E> il) noexcept;      // C++17
451
452}  // std
453
454*/
455
456#include <__config>
457#include <iosfwd> // for forward declarations of vector and string.
458#include <__functional_base>
459#include <type_traits>
460#include <compare>
461#include <concepts> // Mandated by the Standard.
462#include <cstddef>
463#include <initializer_list>
464#include <__iterator/concepts.h>
465#include <__iterator/incrementable_traits.h>
466#include <__iterator/iter_move.h>
467#include <__iterator/iterator_traits.h>
468#include <__iterator/readable_traits.h>
469#include <__iterator/concepts.h>
470#include <__memory/addressof.h>
471#include <__memory/pointer_traits.h>
472#include <version>
473
474#include <__debug>
475
476#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
477#pragma GCC system_header
478#endif
479
480_LIBCPP_BEGIN_NAMESPACE_STD
481
482template<class _Category, class _Tp, class _Distance = ptrdiff_t,
483         class _Pointer = _Tp*, class _Reference = _Tp&>
484struct _LIBCPP_TEMPLATE_VIS iterator
485{
486    typedef _Tp        value_type;
487    typedef _Distance  difference_type;
488    typedef _Pointer   pointer;
489    typedef _Reference reference;
490    typedef _Category  iterator_category;
491};
492
493template <class _InputIter>
494inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
495void __advance(_InputIter& __i,
496             typename iterator_traits<_InputIter>::difference_type __n, input_iterator_tag)
497{
498    for (; __n > 0; --__n)
499        ++__i;
500}
501
502template <class _BiDirIter>
503inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
504void __advance(_BiDirIter& __i,
505             typename iterator_traits<_BiDirIter>::difference_type __n, bidirectional_iterator_tag)
506{
507    if (__n >= 0)
508        for (; __n > 0; --__n)
509            ++__i;
510    else
511        for (; __n < 0; ++__n)
512            --__i;
513}
514
515template <class _RandIter>
516inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
517void __advance(_RandIter& __i,
518             typename iterator_traits<_RandIter>::difference_type __n, random_access_iterator_tag)
519{
520   __i += __n;
521}
522
523template <class _InputIter, class _Distance>
524inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
525void advance(_InputIter& __i, _Distance __orig_n)
526{
527    _LIBCPP_ASSERT(__orig_n >= 0 || __is_cpp17_bidirectional_iterator<_InputIter>::value,
528                   "Attempt to advance(it, n) with negative n on a non-bidirectional iterator");
529    typedef decltype(_VSTD::__convert_to_integral(__orig_n)) _IntegralSize;
530    _IntegralSize __n = __orig_n;
531    _VSTD::__advance(__i, __n, typename iterator_traits<_InputIter>::iterator_category());
532}
533
534template <class _InputIter>
535inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
536typename iterator_traits<_InputIter>::difference_type
537__distance(_InputIter __first, _InputIter __last, input_iterator_tag)
538{
539    typename iterator_traits<_InputIter>::difference_type __r(0);
540    for (; __first != __last; ++__first)
541        ++__r;
542    return __r;
543}
544
545template <class _RandIter>
546inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
547typename iterator_traits<_RandIter>::difference_type
548__distance(_RandIter __first, _RandIter __last, random_access_iterator_tag)
549{
550    return __last - __first;
551}
552
553template <class _InputIter>
554inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
555typename iterator_traits<_InputIter>::difference_type
556distance(_InputIter __first, _InputIter __last)
557{
558    return _VSTD::__distance(__first, __last, typename iterator_traits<_InputIter>::iterator_category());
559}
560
561template <class _InputIter>
562inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
563typename enable_if
564<
565    __is_cpp17_input_iterator<_InputIter>::value,
566    _InputIter
567>::type
568next(_InputIter __x,
569     typename iterator_traits<_InputIter>::difference_type __n = 1)
570{
571    _LIBCPP_ASSERT(__n >= 0 || __is_cpp17_bidirectional_iterator<_InputIter>::value,
572                       "Attempt to next(it, n) with negative n on a non-bidirectional iterator");
573
574    _VSTD::advance(__x, __n);
575    return __x;
576}
577
578template <class _InputIter>
579inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
580typename enable_if
581<
582    __is_cpp17_input_iterator<_InputIter>::value,
583    _InputIter
584>::type
585prev(_InputIter __x,
586     typename iterator_traits<_InputIter>::difference_type __n = 1)
587{
588    _LIBCPP_ASSERT(__n <= 0 || __is_cpp17_bidirectional_iterator<_InputIter>::value,
589                       "Attempt to prev(it, n) with a positive n on a non-bidirectional iterator");
590    _VSTD::advance(__x, -__n);
591    return __x;
592}
593
594
595template <class _Tp, class = void>
596struct __is_stashing_iterator : false_type {};
597
598template <class _Tp>
599struct __is_stashing_iterator<_Tp, typename __void_t<typename _Tp::__stashing_iterator_tag>::type>
600  : true_type {};
601
602template <class _Iter>
603class _LIBCPP_TEMPLATE_VIS reverse_iterator
604    : public iterator<typename iterator_traits<_Iter>::iterator_category,
605                      typename iterator_traits<_Iter>::value_type,
606                      typename iterator_traits<_Iter>::difference_type,
607                      typename iterator_traits<_Iter>::pointer,
608                      typename iterator_traits<_Iter>::reference>
609{
610private:
611    /*mutable*/ _Iter __t;  // no longer used as of LWG #2360, not removed due to ABI break
612
613    static_assert(!__is_stashing_iterator<_Iter>::value,
614      "The specified iterator type cannot be used with reverse_iterator; "
615      "Using stashing iterators with reverse_iterator causes undefined behavior");
616
617protected:
618    _Iter current;
619public:
620    typedef _Iter                                            iterator_type;
621    typedef typename iterator_traits<_Iter>::difference_type difference_type;
622    typedef typename iterator_traits<_Iter>::reference       reference;
623    typedef typename iterator_traits<_Iter>::pointer         pointer;
624    typedef _If<__is_cpp17_random_access_iterator<_Iter>::value,
625        random_access_iterator_tag,
626        typename iterator_traits<_Iter>::iterator_category>  iterator_category;
627#if _LIBCPP_STD_VER > 17
628    typedef _If<__is_cpp17_random_access_iterator<_Iter>::value,
629        random_access_iterator_tag,
630        bidirectional_iterator_tag>                          iterator_concept;
631#endif
632
633    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
634    reverse_iterator() : __t(), current() {}
635    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
636    explicit reverse_iterator(_Iter __x) : __t(__x), current(__x) {}
637    template <class _Up>
638        _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
639        reverse_iterator(const reverse_iterator<_Up>& __u) : __t(__u.base()), current(__u.base()) {}
640    template <class _Up>
641        _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
642        reverse_iterator& operator=(const reverse_iterator<_Up>& __u)
643            { __t = current = __u.base(); return *this; }
644    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
645    _Iter base() const {return current;}
646    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
647    reference operator*() const {_Iter __tmp = current; return *--__tmp;}
648    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
649    pointer  operator->() const {return _VSTD::addressof(operator*());}
650    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
651    reverse_iterator& operator++() {--current; return *this;}
652    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
653    reverse_iterator  operator++(int) {reverse_iterator __tmp(*this); --current; return __tmp;}
654    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
655    reverse_iterator& operator--() {++current; return *this;}
656    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
657    reverse_iterator  operator--(int) {reverse_iterator __tmp(*this); ++current; return __tmp;}
658    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
659    reverse_iterator  operator+ (difference_type __n) const {return reverse_iterator(current - __n);}
660    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
661    reverse_iterator& operator+=(difference_type __n) {current -= __n; return *this;}
662    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
663    reverse_iterator  operator- (difference_type __n) const {return reverse_iterator(current + __n);}
664    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
665    reverse_iterator& operator-=(difference_type __n) {current += __n; return *this;}
666    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
667    reference         operator[](difference_type __n) const {return *(*this + __n);}
668};
669
670template <class _Iter1, class _Iter2>
671inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
672bool
673operator==(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
674{
675    return __x.base() == __y.base();
676}
677
678template <class _Iter1, class _Iter2>
679inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
680bool
681operator<(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
682{
683    return __x.base() > __y.base();
684}
685
686template <class _Iter1, class _Iter2>
687inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
688bool
689operator!=(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
690{
691    return __x.base() != __y.base();
692}
693
694template <class _Iter1, class _Iter2>
695inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
696bool
697operator>(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
698{
699    return __x.base() < __y.base();
700}
701
702template <class _Iter1, class _Iter2>
703inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
704bool
705operator>=(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
706{
707    return __x.base() <= __y.base();
708}
709
710template <class _Iter1, class _Iter2>
711inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
712bool
713operator<=(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
714{
715    return __x.base() >= __y.base();
716}
717
718#ifndef _LIBCPP_CXX03_LANG
719template <class _Iter1, class _Iter2>
720inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
721auto
722operator-(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
723-> decltype(__y.base() - __x.base())
724{
725    return __y.base() - __x.base();
726}
727#else
728template <class _Iter1, class _Iter2>
729inline _LIBCPP_INLINE_VISIBILITY
730typename reverse_iterator<_Iter1>::difference_type
731operator-(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
732{
733    return __y.base() - __x.base();
734}
735#endif
736
737template <class _Iter>
738inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
739reverse_iterator<_Iter>
740operator+(typename reverse_iterator<_Iter>::difference_type __n, const reverse_iterator<_Iter>& __x)
741{
742    return reverse_iterator<_Iter>(__x.base() - __n);
743}
744
745#if _LIBCPP_STD_VER > 11
746template <class _Iter>
747inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
748reverse_iterator<_Iter> make_reverse_iterator(_Iter __i)
749{
750    return reverse_iterator<_Iter>(__i);
751}
752#endif
753
754template <class _Container>
755class _LIBCPP_TEMPLATE_VIS back_insert_iterator
756    : public iterator<output_iterator_tag,
757                      void,
758                      void,
759                      void,
760                      void>
761{
762protected:
763    _Container* container;
764public:
765    typedef _Container container_type;
766
767    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 explicit back_insert_iterator(_Container& __x) : container(_VSTD::addressof(__x)) {}
768    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator& operator=(const typename _Container::value_type& __value_)
769        {container->push_back(__value_); return *this;}
770#ifndef _LIBCPP_CXX03_LANG
771    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator& operator=(typename _Container::value_type&& __value_)
772        {container->push_back(_VSTD::move(__value_)); return *this;}
773#endif // _LIBCPP_CXX03_LANG
774    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator& operator*()     {return *this;}
775    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator& operator++()    {return *this;}
776    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator  operator++(int) {return *this;}
777};
778
779template <class _Container>
780inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
781back_insert_iterator<_Container>
782back_inserter(_Container& __x)
783{
784    return back_insert_iterator<_Container>(__x);
785}
786
787template <class _Container>
788class _LIBCPP_TEMPLATE_VIS front_insert_iterator
789    : public iterator<output_iterator_tag,
790                      void,
791                      void,
792                      void,
793                      void>
794{
795protected:
796    _Container* container;
797public:
798    typedef _Container container_type;
799
800    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 explicit front_insert_iterator(_Container& __x) : container(_VSTD::addressof(__x)) {}
801    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator& operator=(const typename _Container::value_type& __value_)
802        {container->push_front(__value_); return *this;}
803#ifndef _LIBCPP_CXX03_LANG
804    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator& operator=(typename _Container::value_type&& __value_)
805        {container->push_front(_VSTD::move(__value_)); return *this;}
806#endif // _LIBCPP_CXX03_LANG
807    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator& operator*()     {return *this;}
808    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator& operator++()    {return *this;}
809    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator  operator++(int) {return *this;}
810};
811
812template <class _Container>
813inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
814front_insert_iterator<_Container>
815front_inserter(_Container& __x)
816{
817    return front_insert_iterator<_Container>(__x);
818}
819
820template <class _Container>
821class _LIBCPP_TEMPLATE_VIS insert_iterator
822    : public iterator<output_iterator_tag,
823                      void,
824                      void,
825                      void,
826                      void>
827{
828protected:
829    _Container* container;
830    typename _Container::iterator iter;
831public:
832    typedef _Container container_type;
833
834    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator(_Container& __x, typename _Container::iterator __i)
835        : container(_VSTD::addressof(__x)), iter(__i) {}
836    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator=(const typename _Container::value_type& __value_)
837        {iter = container->insert(iter, __value_); ++iter; return *this;}
838#ifndef _LIBCPP_CXX03_LANG
839    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator=(typename _Container::value_type&& __value_)
840        {iter = container->insert(iter, _VSTD::move(__value_)); ++iter; return *this;}
841#endif // _LIBCPP_CXX03_LANG
842    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator*()        {return *this;}
843    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator++()       {return *this;}
844    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator++(int)    {return *this;}
845};
846
847template <class _Container>
848inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
849insert_iterator<_Container>
850inserter(_Container& __x, typename _Container::iterator __i)
851{
852    return insert_iterator<_Container>(__x, __i);
853}
854
855template <class _Tp, class _CharT = char,
856          class _Traits = char_traits<_CharT>, class _Distance = ptrdiff_t>
857class _LIBCPP_TEMPLATE_VIS istream_iterator
858    : public iterator<input_iterator_tag, _Tp, _Distance, const _Tp*, const _Tp&>
859{
860public:
861    typedef _CharT char_type;
862    typedef _Traits traits_type;
863    typedef basic_istream<_CharT,_Traits> istream_type;
864private:
865    istream_type* __in_stream_;
866    _Tp __value_;
867public:
868    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR istream_iterator() : __in_stream_(nullptr), __value_() {}
869    _LIBCPP_INLINE_VISIBILITY istream_iterator(istream_type& __s) : __in_stream_(_VSTD::addressof(__s))
870        {
871            if (!(*__in_stream_ >> __value_))
872                __in_stream_ = nullptr;
873        }
874
875    _LIBCPP_INLINE_VISIBILITY const _Tp& operator*() const {return __value_;}
876    _LIBCPP_INLINE_VISIBILITY const _Tp* operator->() const {return _VSTD::addressof((operator*()));}
877    _LIBCPP_INLINE_VISIBILITY istream_iterator& operator++()
878        {
879            if (!(*__in_stream_ >> __value_))
880                __in_stream_ = nullptr;
881            return *this;
882        }
883    _LIBCPP_INLINE_VISIBILITY istream_iterator  operator++(int)
884        {istream_iterator __t(*this); ++(*this); return __t;}
885
886    template <class _Up, class _CharU, class _TraitsU, class _DistanceU>
887    friend _LIBCPP_INLINE_VISIBILITY
888    bool
889    operator==(const istream_iterator<_Up, _CharU, _TraitsU, _DistanceU>& __x,
890               const istream_iterator<_Up, _CharU, _TraitsU, _DistanceU>& __y);
891
892    template <class _Up, class _CharU, class _TraitsU, class _DistanceU>
893    friend _LIBCPP_INLINE_VISIBILITY
894    bool
895    operator==(const istream_iterator<_Up, _CharU, _TraitsU, _DistanceU>& __x,
896               const istream_iterator<_Up, _CharU, _TraitsU, _DistanceU>& __y);
897};
898
899template <class _Tp, class _CharT, class _Traits, class _Distance>
900inline _LIBCPP_INLINE_VISIBILITY
901bool
902operator==(const istream_iterator<_Tp, _CharT, _Traits, _Distance>& __x,
903           const istream_iterator<_Tp, _CharT, _Traits, _Distance>& __y)
904{
905    return __x.__in_stream_ == __y.__in_stream_;
906}
907
908template <class _Tp, class _CharT, class _Traits, class _Distance>
909inline _LIBCPP_INLINE_VISIBILITY
910bool
911operator!=(const istream_iterator<_Tp, _CharT, _Traits, _Distance>& __x,
912           const istream_iterator<_Tp, _CharT, _Traits, _Distance>& __y)
913{
914    return !(__x == __y);
915}
916
917template <class _Tp, class _CharT = char, class _Traits = char_traits<_CharT> >
918class _LIBCPP_TEMPLATE_VIS ostream_iterator
919    : public iterator<output_iterator_tag, void, void, void, void>
920{
921public:
922    typedef output_iterator_tag             iterator_category;
923    typedef void                            value_type;
924#if _LIBCPP_STD_VER > 17
925    typedef std::ptrdiff_t                  difference_type;
926#else
927    typedef void                            difference_type;
928#endif
929    typedef void                            pointer;
930    typedef void                            reference;
931    typedef _CharT                          char_type;
932    typedef _Traits                         traits_type;
933    typedef basic_ostream<_CharT, _Traits>  ostream_type;
934
935private:
936    ostream_type* __out_stream_;
937    const char_type* __delim_;
938public:
939    _LIBCPP_INLINE_VISIBILITY ostream_iterator(ostream_type& __s) _NOEXCEPT
940        : __out_stream_(_VSTD::addressof(__s)), __delim_(nullptr) {}
941    _LIBCPP_INLINE_VISIBILITY ostream_iterator(ostream_type& __s, const _CharT* __delimiter) _NOEXCEPT
942        : __out_stream_(_VSTD::addressof(__s)), __delim_(__delimiter) {}
943    _LIBCPP_INLINE_VISIBILITY ostream_iterator& operator=(const _Tp& __value_)
944        {
945            *__out_stream_ << __value_;
946            if (__delim_)
947                *__out_stream_ << __delim_;
948            return *this;
949        }
950
951    _LIBCPP_INLINE_VISIBILITY ostream_iterator& operator*()     {return *this;}
952    _LIBCPP_INLINE_VISIBILITY ostream_iterator& operator++()    {return *this;}
953    _LIBCPP_INLINE_VISIBILITY ostream_iterator& operator++(int) {return *this;}
954};
955
956template<class _CharT, class _Traits>
957class _LIBCPP_TEMPLATE_VIS istreambuf_iterator
958    : public iterator<input_iterator_tag, _CharT,
959                      typename _Traits::off_type, _CharT*,
960                      _CharT>
961{
962public:
963    typedef _CharT                          char_type;
964    typedef _Traits                         traits_type;
965    typedef typename _Traits::int_type      int_type;
966    typedef basic_streambuf<_CharT,_Traits> streambuf_type;
967    typedef basic_istream<_CharT,_Traits>   istream_type;
968private:
969    mutable streambuf_type* __sbuf_;
970
971    class __proxy
972    {
973        char_type __keep_;
974        streambuf_type* __sbuf_;
975        _LIBCPP_INLINE_VISIBILITY __proxy(char_type __c, streambuf_type* __s)
976            : __keep_(__c), __sbuf_(__s) {}
977        friend class istreambuf_iterator;
978    public:
979        _LIBCPP_INLINE_VISIBILITY char_type operator*() const {return __keep_;}
980    };
981
982    _LIBCPP_INLINE_VISIBILITY
983    bool __test_for_eof() const
984    {
985        if (__sbuf_ && traits_type::eq_int_type(__sbuf_->sgetc(), traits_type::eof()))
986            __sbuf_ = nullptr;
987        return __sbuf_ == nullptr;
988    }
989public:
990    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR istreambuf_iterator() _NOEXCEPT : __sbuf_(nullptr) {}
991    _LIBCPP_INLINE_VISIBILITY istreambuf_iterator(istream_type& __s) _NOEXCEPT
992        : __sbuf_(__s.rdbuf()) {}
993    _LIBCPP_INLINE_VISIBILITY istreambuf_iterator(streambuf_type* __s) _NOEXCEPT
994        : __sbuf_(__s) {}
995    _LIBCPP_INLINE_VISIBILITY istreambuf_iterator(const __proxy& __p) _NOEXCEPT
996        : __sbuf_(__p.__sbuf_) {}
997
998    _LIBCPP_INLINE_VISIBILITY char_type  operator*() const
999        {return static_cast<char_type>(__sbuf_->sgetc());}
1000    _LIBCPP_INLINE_VISIBILITY istreambuf_iterator& operator++()
1001        {
1002            __sbuf_->sbumpc();
1003            return *this;
1004        }
1005    _LIBCPP_INLINE_VISIBILITY __proxy              operator++(int)
1006        {
1007            return __proxy(__sbuf_->sbumpc(), __sbuf_);
1008        }
1009
1010    _LIBCPP_INLINE_VISIBILITY bool equal(const istreambuf_iterator& __b) const
1011        {return __test_for_eof() == __b.__test_for_eof();}
1012};
1013
1014template <class _CharT, class _Traits>
1015inline _LIBCPP_INLINE_VISIBILITY
1016bool operator==(const istreambuf_iterator<_CharT,_Traits>& __a,
1017                const istreambuf_iterator<_CharT,_Traits>& __b)
1018                {return __a.equal(__b);}
1019
1020template <class _CharT, class _Traits>
1021inline _LIBCPP_INLINE_VISIBILITY
1022bool operator!=(const istreambuf_iterator<_CharT,_Traits>& __a,
1023                const istreambuf_iterator<_CharT,_Traits>& __b)
1024                {return !__a.equal(__b);}
1025
1026template <class _CharT, class _Traits>
1027class _LIBCPP_TEMPLATE_VIS ostreambuf_iterator
1028    : public iterator<output_iterator_tag, void, void, void, void>
1029{
1030public:
1031    typedef output_iterator_tag                 iterator_category;
1032    typedef void                                value_type;
1033#if _LIBCPP_STD_VER > 17
1034    typedef std::ptrdiff_t                      difference_type;
1035#else
1036    typedef void                                difference_type;
1037#endif
1038    typedef void                                pointer;
1039    typedef void                                reference;
1040    typedef _CharT                              char_type;
1041    typedef _Traits                             traits_type;
1042    typedef basic_streambuf<_CharT, _Traits>    streambuf_type;
1043    typedef basic_ostream<_CharT, _Traits>      ostream_type;
1044
1045private:
1046    streambuf_type* __sbuf_;
1047public:
1048    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator(ostream_type& __s) _NOEXCEPT
1049        : __sbuf_(__s.rdbuf()) {}
1050    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator(streambuf_type* __s) _NOEXCEPT
1051        : __sbuf_(__s) {}
1052    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator& operator=(_CharT __c)
1053        {
1054            if (__sbuf_ && traits_type::eq_int_type(__sbuf_->sputc(__c), traits_type::eof()))
1055                __sbuf_ = nullptr;
1056            return *this;
1057        }
1058    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator& operator*()     {return *this;}
1059    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator& operator++()    {return *this;}
1060    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator& operator++(int) {return *this;}
1061    _LIBCPP_INLINE_VISIBILITY bool failed() const _NOEXCEPT {return __sbuf_ == nullptr;}
1062
1063    template <class _Ch, class _Tr>
1064    friend
1065    _LIBCPP_HIDDEN
1066    ostreambuf_iterator<_Ch, _Tr>
1067    __pad_and_output(ostreambuf_iterator<_Ch, _Tr> __s,
1068                     const _Ch* __ob, const _Ch* __op, const _Ch* __oe,
1069                     ios_base& __iob, _Ch __fl);
1070};
1071
1072template <class _Iter>
1073class _LIBCPP_TEMPLATE_VIS move_iterator
1074{
1075private:
1076    _Iter __i;
1077public:
1078    typedef _Iter                                            iterator_type;
1079    typedef typename iterator_traits<iterator_type>::value_type value_type;
1080    typedef typename iterator_traits<iterator_type>::difference_type difference_type;
1081    typedef iterator_type pointer;
1082    typedef _If<__is_cpp17_random_access_iterator<_Iter>::value,
1083        random_access_iterator_tag,
1084        typename iterator_traits<_Iter>::iterator_category>  iterator_category;
1085#if _LIBCPP_STD_VER > 17
1086    typedef input_iterator_tag                               iterator_concept;
1087#endif
1088
1089#ifndef _LIBCPP_CXX03_LANG
1090    typedef typename iterator_traits<iterator_type>::reference __reference;
1091    typedef typename conditional<
1092            is_reference<__reference>::value,
1093            typename remove_reference<__reference>::type&&,
1094            __reference
1095        >::type reference;
1096#else
1097    typedef typename iterator_traits<iterator_type>::reference reference;
1098#endif
1099
1100    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1101    move_iterator() : __i() {}
1102    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1103    explicit move_iterator(_Iter __x) : __i(__x) {}
1104    template <class _Up>
1105      _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1106      move_iterator(const move_iterator<_Up>& __u) : __i(__u.base()) {}
1107    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14 _Iter base() const {return __i;}
1108    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1109    reference operator*() const { return static_cast<reference>(*__i); }
1110    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1111    pointer  operator->() const { return __i;}
1112    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1113    move_iterator& operator++() {++__i; return *this;}
1114    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1115    move_iterator  operator++(int) {move_iterator __tmp(*this); ++__i; return __tmp;}
1116    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1117    move_iterator& operator--() {--__i; return *this;}
1118    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1119    move_iterator  operator--(int) {move_iterator __tmp(*this); --__i; return __tmp;}
1120    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1121    move_iterator  operator+ (difference_type __n) const {return move_iterator(__i + __n);}
1122    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1123    move_iterator& operator+=(difference_type __n) {__i += __n; return *this;}
1124    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1125    move_iterator  operator- (difference_type __n) const {return move_iterator(__i - __n);}
1126    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1127    move_iterator& operator-=(difference_type __n) {__i -= __n; return *this;}
1128    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1129    reference operator[](difference_type __n) const { return static_cast<reference>(__i[__n]); }
1130};
1131
1132template <class _Iter1, class _Iter2>
1133inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1134bool
1135operator==(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
1136{
1137    return __x.base() == __y.base();
1138}
1139
1140template <class _Iter1, class _Iter2>
1141inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1142bool
1143operator<(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
1144{
1145    return __x.base() < __y.base();
1146}
1147
1148template <class _Iter1, class _Iter2>
1149inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1150bool
1151operator!=(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
1152{
1153    return __x.base() != __y.base();
1154}
1155
1156template <class _Iter1, class _Iter2>
1157inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1158bool
1159operator>(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
1160{
1161    return __x.base() > __y.base();
1162}
1163
1164template <class _Iter1, class _Iter2>
1165inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1166bool
1167operator>=(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
1168{
1169    return __x.base() >= __y.base();
1170}
1171
1172template <class _Iter1, class _Iter2>
1173inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1174bool
1175operator<=(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
1176{
1177    return __x.base() <= __y.base();
1178}
1179
1180#ifndef _LIBCPP_CXX03_LANG
1181template <class _Iter1, class _Iter2>
1182inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1183auto
1184operator-(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
1185-> decltype(__x.base() - __y.base())
1186{
1187    return __x.base() - __y.base();
1188}
1189#else
1190template <class _Iter1, class _Iter2>
1191inline _LIBCPP_INLINE_VISIBILITY
1192typename move_iterator<_Iter1>::difference_type
1193operator-(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
1194{
1195    return __x.base() - __y.base();
1196}
1197#endif
1198
1199template <class _Iter>
1200inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1201move_iterator<_Iter>
1202operator+(typename move_iterator<_Iter>::difference_type __n, const move_iterator<_Iter>& __x)
1203{
1204    return move_iterator<_Iter>(__x.base() + __n);
1205}
1206
1207template <class _Iter>
1208inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1209move_iterator<_Iter>
1210make_move_iterator(_Iter __i)
1211{
1212    return move_iterator<_Iter>(__i);
1213}
1214
1215// __wrap_iter
1216
1217template <class _Iter> class __wrap_iter;
1218
1219template <class _Iter1, class _Iter2>
1220_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1221bool
1222operator==(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1223
1224template <class _Iter1, class _Iter2>
1225_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1226bool
1227operator<(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1228
1229template <class _Iter1, class _Iter2>
1230_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1231bool
1232operator!=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1233
1234template <class _Iter1, class _Iter2>
1235_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1236bool
1237operator>(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1238
1239template <class _Iter1, class _Iter2>
1240_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1241bool
1242operator>=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1243
1244template <class _Iter1, class _Iter2>
1245_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1246bool
1247operator<=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1248
1249#ifndef _LIBCPP_CXX03_LANG
1250template <class _Iter1, class _Iter2>
1251_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1252auto
1253operator-(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
1254-> decltype(__x.base() - __y.base());
1255#else
1256template <class _Iter1, class _Iter2>
1257_LIBCPP_INLINE_VISIBILITY
1258typename __wrap_iter<_Iter1>::difference_type
1259operator-(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1260#endif
1261
1262template <class _Iter>
1263_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1264__wrap_iter<_Iter>
1265operator+(typename __wrap_iter<_Iter>::difference_type, __wrap_iter<_Iter>) _NOEXCEPT;
1266
1267template <class _Ip, class _Op> _Op _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 copy(_Ip, _Ip, _Op);
1268template <class _B1, class _B2> _B2 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 copy_backward(_B1, _B1, _B2);
1269template <class _Ip, class _Op> _Op _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 move(_Ip, _Ip, _Op);
1270template <class _B1, class _B2> _B2 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 move_backward(_B1, _B1, _B2);
1271
1272template <class _Iter>
1273class __wrap_iter
1274{
1275public:
1276    typedef _Iter                                                      iterator_type;
1277    typedef typename iterator_traits<iterator_type>::value_type        value_type;
1278    typedef typename iterator_traits<iterator_type>::difference_type   difference_type;
1279    typedef typename iterator_traits<iterator_type>::pointer           pointer;
1280    typedef typename iterator_traits<iterator_type>::reference         reference;
1281    typedef typename iterator_traits<iterator_type>::iterator_category iterator_category;
1282#if _LIBCPP_STD_VER > 17
1283    typedef _If<__is_cpp17_contiguous_iterator<_Iter>::value,
1284                contiguous_iterator_tag, iterator_category>            iterator_concept;
1285#endif
1286
1287private:
1288    iterator_type __i;
1289public:
1290    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter() _NOEXCEPT
1291#if _LIBCPP_STD_VER > 11
1292                : __i{}
1293#endif
1294    {
1295#if _LIBCPP_DEBUG_LEVEL == 2
1296        __get_db()->__insert_i(this);
1297#endif
1298    }
1299    template <class _Up> _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1300        __wrap_iter(const __wrap_iter<_Up>& __u,
1301            typename enable_if<is_convertible<_Up, iterator_type>::value>::type* = nullptr) _NOEXCEPT
1302            : __i(__u.base())
1303    {
1304#if _LIBCPP_DEBUG_LEVEL == 2
1305        __get_db()->__iterator_copy(this, &__u);
1306#endif
1307    }
1308#if _LIBCPP_DEBUG_LEVEL == 2
1309    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1310    __wrap_iter(const __wrap_iter& __x)
1311        : __i(__x.base())
1312    {
1313        __get_db()->__iterator_copy(this, &__x);
1314    }
1315    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1316    __wrap_iter& operator=(const __wrap_iter& __x)
1317    {
1318        if (this != &__x)
1319        {
1320            __get_db()->__iterator_copy(this, &__x);
1321            __i = __x.__i;
1322        }
1323        return *this;
1324    }
1325    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1326    ~__wrap_iter()
1327    {
1328        __get_db()->__erase_i(this);
1329    }
1330#endif
1331    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG reference operator*() const _NOEXCEPT
1332    {
1333#if _LIBCPP_DEBUG_LEVEL == 2
1334        _LIBCPP_ASSERT(__get_const_db()->__dereferenceable(this),
1335                       "Attempted to dereference a non-dereferenceable iterator");
1336#endif
1337        return *__i;
1338    }
1339    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG pointer  operator->() const _NOEXCEPT
1340    {
1341#if _LIBCPP_DEBUG_LEVEL == 2
1342        _LIBCPP_ASSERT(__get_const_db()->__dereferenceable(this),
1343                       "Attempted to dereference a non-dereferenceable iterator");
1344#endif
1345        return (pointer)_VSTD::addressof(*__i);
1346    }
1347    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter& operator++() _NOEXCEPT
1348    {
1349#if _LIBCPP_DEBUG_LEVEL == 2
1350        _LIBCPP_ASSERT(__get_const_db()->__dereferenceable(this),
1351                       "Attempted to increment non-incrementable iterator");
1352#endif
1353        ++__i;
1354        return *this;
1355    }
1356    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter  operator++(int) _NOEXCEPT
1357        {__wrap_iter __tmp(*this); ++(*this); return __tmp;}
1358
1359    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter& operator--() _NOEXCEPT
1360    {
1361#if _LIBCPP_DEBUG_LEVEL == 2
1362        _LIBCPP_ASSERT(__get_const_db()->__decrementable(this),
1363                       "Attempted to decrement non-decrementable iterator");
1364#endif
1365        --__i;
1366        return *this;
1367    }
1368    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter  operator--(int) _NOEXCEPT
1369        {__wrap_iter __tmp(*this); --(*this); return __tmp;}
1370    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter  operator+ (difference_type __n) const _NOEXCEPT
1371        {__wrap_iter __w(*this); __w += __n; return __w;}
1372    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter& operator+=(difference_type __n) _NOEXCEPT
1373    {
1374#if _LIBCPP_DEBUG_LEVEL == 2
1375        _LIBCPP_ASSERT(__get_const_db()->__addable(this, __n),
1376                   "Attempted to add/subtract iterator outside of valid range");
1377#endif
1378        __i += __n;
1379        return *this;
1380    }
1381    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter  operator- (difference_type __n) const _NOEXCEPT
1382        {return *this + (-__n);}
1383    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter& operator-=(difference_type __n) _NOEXCEPT
1384        {*this += -__n; return *this;}
1385    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG reference    operator[](difference_type __n) const _NOEXCEPT
1386    {
1387#if _LIBCPP_DEBUG_LEVEL == 2
1388        _LIBCPP_ASSERT(__get_const_db()->__subscriptable(this, __n),
1389                   "Attempted to subscript iterator outside of valid range");
1390#endif
1391        return __i[__n];
1392    }
1393
1394    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG iterator_type base() const _NOEXCEPT {return __i;}
1395
1396private:
1397#if _LIBCPP_DEBUG_LEVEL == 2
1398    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter(const void* __p, iterator_type __x) : __i(__x)
1399    {
1400        __get_db()->__insert_ic(this, __p);
1401    }
1402#else
1403    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter(iterator_type __x) _NOEXCEPT : __i(__x) {}
1404#endif
1405
1406    template <class _Up> friend class __wrap_iter;
1407    template <class _CharT, class _Traits, class _Alloc> friend class basic_string;
1408    template <class _Tp, class _Alloc> friend class _LIBCPP_TEMPLATE_VIS vector;
1409    template <class _Tp, size_t> friend class _LIBCPP_TEMPLATE_VIS span;
1410
1411    template <class _Iter1, class _Iter2>
1412    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
1413    bool
1414    operator==(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1415
1416    template <class _Iter1, class _Iter2>
1417    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
1418    bool
1419    operator<(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1420
1421    template <class _Iter1, class _Iter2>
1422    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
1423    bool
1424    operator!=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1425
1426    template <class _Iter1, class _Iter2>
1427    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
1428    bool
1429    operator>(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1430
1431    template <class _Iter1, class _Iter2>
1432    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
1433    bool
1434    operator>=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1435
1436    template <class _Iter1, class _Iter2>
1437    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
1438    bool
1439    operator<=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1440
1441#ifndef _LIBCPP_CXX03_LANG
1442    template <class _Iter1, class _Iter2>
1443    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
1444    auto
1445    operator-(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
1446    -> decltype(__x.base() - __y.base());
1447#else
1448    template <class _Iter1, class _Iter2>
1449    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
1450    typename __wrap_iter<_Iter1>::difference_type
1451    operator-(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
1452#endif
1453
1454    template <class _Iter1>
1455    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
1456    __wrap_iter<_Iter1>
1457    operator+(typename __wrap_iter<_Iter1>::difference_type, __wrap_iter<_Iter1>) _NOEXCEPT;
1458
1459    template <class _Ip, class _Op> friend _LIBCPP_CONSTEXPR_AFTER_CXX17 _Op copy(_Ip, _Ip, _Op);
1460    template <class _B1, class _B2> friend _LIBCPP_CONSTEXPR_AFTER_CXX17 _B2 copy_backward(_B1, _B1, _B2);
1461    template <class _Ip, class _Op> friend _LIBCPP_CONSTEXPR_AFTER_CXX17 _Op move(_Ip, _Ip, _Op);
1462    template <class _B1, class _B2> friend _LIBCPP_CONSTEXPR_AFTER_CXX17 _B2 move_backward(_B1, _B1, _B2);
1463};
1464
1465#if _LIBCPP_STD_VER <= 17
1466template <class _It>
1467struct __is_cpp17_contiguous_iterator<__wrap_iter<_It> > : __is_cpp17_contiguous_iterator<_It> {};
1468#endif
1469
1470template <class _Iter>
1471_LIBCPP_CONSTEXPR
1472_EnableIf<__is_cpp17_contiguous_iterator<_Iter>::value, decltype(_VSTD::__to_address(declval<_Iter>()))>
1473__to_address(__wrap_iter<_Iter> __w) _NOEXCEPT {
1474    return _VSTD::__to_address(__w.base());
1475}
1476
1477template <class _Iter1, class _Iter2>
1478inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1479bool
1480operator==(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
1481{
1482    return __x.base() == __y.base();
1483}
1484
1485template <class _Iter1, class _Iter2>
1486inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1487bool
1488operator<(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
1489{
1490#if _LIBCPP_DEBUG_LEVEL == 2
1491    _LIBCPP_ASSERT(__get_const_db()->__less_than_comparable(&__x, &__y),
1492                   "Attempted to compare incomparable iterators");
1493#endif
1494    return __x.base() < __y.base();
1495}
1496
1497template <class _Iter1, class _Iter2>
1498inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1499bool
1500operator!=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
1501{
1502    return !(__x == __y);
1503}
1504
1505template <class _Iter1, class _Iter2>
1506inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1507bool
1508operator>(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
1509{
1510    return __y < __x;
1511}
1512
1513template <class _Iter1, class _Iter2>
1514inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1515bool
1516operator>=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
1517{
1518    return !(__x < __y);
1519}
1520
1521template <class _Iter1, class _Iter2>
1522inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1523bool
1524operator<=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
1525{
1526    return !(__y < __x);
1527}
1528
1529template <class _Iter1>
1530inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1531bool
1532operator!=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter1>& __y) _NOEXCEPT
1533{
1534    return !(__x == __y);
1535}
1536
1537template <class _Iter1>
1538inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1539bool
1540operator>(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter1>& __y) _NOEXCEPT
1541{
1542    return __y < __x;
1543}
1544
1545template <class _Iter1>
1546inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1547bool
1548operator>=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter1>& __y) _NOEXCEPT
1549{
1550    return !(__x < __y);
1551}
1552
1553template <class _Iter1>
1554inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1555bool
1556operator<=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter1>& __y) _NOEXCEPT
1557{
1558    return !(__y < __x);
1559}
1560
1561#ifndef _LIBCPP_CXX03_LANG
1562template <class _Iter1, class _Iter2>
1563inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1564auto
1565operator-(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
1566-> decltype(__x.base() - __y.base())
1567{
1568#if _LIBCPP_DEBUG_LEVEL == 2
1569    _LIBCPP_ASSERT(__get_const_db()->__less_than_comparable(&__x, &__y),
1570                   "Attempted to subtract incompatible iterators");
1571#endif
1572    return __x.base() - __y.base();
1573}
1574#else
1575template <class _Iter1, class _Iter2>
1576inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1577typename __wrap_iter<_Iter1>::difference_type
1578operator-(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
1579{
1580#if _LIBCPP_DEBUG_LEVEL == 2
1581    _LIBCPP_ASSERT(__get_const_db()->__less_than_comparable(&__x, &__y),
1582                   "Attempted to subtract incompatible iterators");
1583#endif
1584    return __x.base() - __y.base();
1585}
1586#endif
1587
1588template <class _Iter>
1589inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
1590__wrap_iter<_Iter>
1591operator+(typename __wrap_iter<_Iter>::difference_type __n,
1592          __wrap_iter<_Iter> __x) _NOEXCEPT
1593{
1594    __x += __n;
1595    return __x;
1596}
1597
1598template <class _Tp, size_t _Np>
1599_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
1600_Tp*
1601begin(_Tp (&__array)[_Np])
1602{
1603    return __array;
1604}
1605
1606template <class _Tp, size_t _Np>
1607_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
1608_Tp*
1609end(_Tp (&__array)[_Np])
1610{
1611    return __array + _Np;
1612}
1613
1614#if !defined(_LIBCPP_CXX03_LANG)
1615
1616template <class _Cp>
1617_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1618auto
1619begin(_Cp& __c) -> decltype(__c.begin())
1620{
1621    return __c.begin();
1622}
1623
1624template <class _Cp>
1625_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1626auto
1627begin(const _Cp& __c) -> decltype(__c.begin())
1628{
1629    return __c.begin();
1630}
1631
1632template <class _Cp>
1633_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1634auto
1635end(_Cp& __c) -> decltype(__c.end())
1636{
1637    return __c.end();
1638}
1639
1640template <class _Cp>
1641_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1642auto
1643end(const _Cp& __c) -> decltype(__c.end())
1644{
1645    return __c.end();
1646}
1647
1648#if _LIBCPP_STD_VER > 11
1649
1650template <class _Tp, size_t _Np>
1651_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1652reverse_iterator<_Tp*> rbegin(_Tp (&__array)[_Np])
1653{
1654    return reverse_iterator<_Tp*>(__array + _Np);
1655}
1656
1657template <class _Tp, size_t _Np>
1658_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1659reverse_iterator<_Tp*> rend(_Tp (&__array)[_Np])
1660{
1661    return reverse_iterator<_Tp*>(__array);
1662}
1663
1664template <class _Ep>
1665_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1666reverse_iterator<const _Ep*> rbegin(initializer_list<_Ep> __il)
1667{
1668    return reverse_iterator<const _Ep*>(__il.end());
1669}
1670
1671template <class _Ep>
1672_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1673reverse_iterator<const _Ep*> rend(initializer_list<_Ep> __il)
1674{
1675    return reverse_iterator<const _Ep*>(__il.begin());
1676}
1677
1678template <class _Cp>
1679_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
1680auto cbegin(const _Cp& __c) -> decltype(_VSTD::begin(__c))
1681{
1682    return _VSTD::begin(__c);
1683}
1684
1685template <class _Cp>
1686_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
1687auto cend(const _Cp& __c) -> decltype(_VSTD::end(__c))
1688{
1689    return _VSTD::end(__c);
1690}
1691
1692template <class _Cp>
1693_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1694auto rbegin(_Cp& __c) -> decltype(__c.rbegin())
1695{
1696    return __c.rbegin();
1697}
1698
1699template <class _Cp>
1700_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1701auto rbegin(const _Cp& __c) -> decltype(__c.rbegin())
1702{
1703    return __c.rbegin();
1704}
1705
1706template <class _Cp>
1707_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1708auto rend(_Cp& __c) -> decltype(__c.rend())
1709{
1710    return __c.rend();
1711}
1712
1713template <class _Cp>
1714_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1715auto rend(const _Cp& __c) -> decltype(__c.rend())
1716{
1717    return __c.rend();
1718}
1719
1720template <class _Cp>
1721_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1722auto crbegin(const _Cp& __c) -> decltype(_VSTD::rbegin(__c))
1723{
1724    return _VSTD::rbegin(__c);
1725}
1726
1727template <class _Cp>
1728_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
1729auto crend(const _Cp& __c) -> decltype(_VSTD::rend(__c))
1730{
1731    return _VSTD::rend(__c);
1732}
1733
1734#endif
1735
1736
1737#else  // defined(_LIBCPP_CXX03_LANG)
1738
1739template <class _Cp>
1740_LIBCPP_INLINE_VISIBILITY
1741typename _Cp::iterator
1742begin(_Cp& __c)
1743{
1744    return __c.begin();
1745}
1746
1747template <class _Cp>
1748_LIBCPP_INLINE_VISIBILITY
1749typename _Cp::const_iterator
1750begin(const _Cp& __c)
1751{
1752    return __c.begin();
1753}
1754
1755template <class _Cp>
1756_LIBCPP_INLINE_VISIBILITY
1757typename _Cp::iterator
1758end(_Cp& __c)
1759{
1760    return __c.end();
1761}
1762
1763template <class _Cp>
1764_LIBCPP_INLINE_VISIBILITY
1765typename _Cp::const_iterator
1766end(const _Cp& __c)
1767{
1768    return __c.end();
1769}
1770
1771#endif // !defined(_LIBCPP_CXX03_LANG)
1772
1773#if _LIBCPP_STD_VER > 14
1774
1775// #if _LIBCPP_STD_VER > 11
1776// template <>
1777// struct _LIBCPP_TEMPLATE_VIS plus<void>
1778// {
1779//     template <class _T1, class _T2>
1780//     _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY
1781//     auto operator()(_T1&& __t, _T2&& __u) const
1782//     _NOEXCEPT_(noexcept(_VSTD::forward<_T1>(__t) + _VSTD::forward<_T2>(__u)))
1783//     -> decltype        (_VSTD::forward<_T1>(__t) + _VSTD::forward<_T2>(__u))
1784//         { return        _VSTD::forward<_T1>(__t) + _VSTD::forward<_T2>(__u); }
1785//     typedef void is_transparent;
1786// };
1787// #endif
1788
1789template <class _Cont>
1790_LIBCPP_INLINE_VISIBILITY
1791constexpr auto size(const _Cont& __c)
1792_NOEXCEPT_(noexcept(__c.size()))
1793-> decltype        (__c.size())
1794{ return            __c.size(); }
1795
1796template <class _Tp, size_t _Sz>
1797_LIBCPP_INLINE_VISIBILITY
1798constexpr size_t size(const _Tp (&)[_Sz]) noexcept { return _Sz; }
1799
1800#if _LIBCPP_STD_VER > 17
1801template <class _Cont>
1802_LIBCPP_INLINE_VISIBILITY
1803constexpr auto ssize(const _Cont& __c)
1804_NOEXCEPT_(noexcept(static_cast<common_type_t<ptrdiff_t, make_signed_t<decltype(__c.size())>>>(__c.size())))
1805->                              common_type_t<ptrdiff_t, make_signed_t<decltype(__c.size())>>
1806{ return            static_cast<common_type_t<ptrdiff_t, make_signed_t<decltype(__c.size())>>>(__c.size()); }
1807
1808template <class _Tp, ptrdiff_t _Sz>
1809_LIBCPP_INLINE_VISIBILITY
1810constexpr ptrdiff_t ssize(const _Tp (&)[_Sz]) noexcept { return _Sz; }
1811#endif
1812
1813template <class _Cont>
1814_LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_INLINE_VISIBILITY
1815constexpr auto empty(const _Cont& __c)
1816_NOEXCEPT_(noexcept(__c.empty()))
1817-> decltype        (__c.empty())
1818{ return            __c.empty(); }
1819
1820template <class _Tp, size_t _Sz>
1821_LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_INLINE_VISIBILITY
1822constexpr bool empty(const _Tp (&)[_Sz]) noexcept { return false; }
1823
1824template <class _Ep>
1825_LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_INLINE_VISIBILITY
1826constexpr bool empty(initializer_list<_Ep> __il) noexcept { return __il.size() == 0; }
1827
1828template <class _Cont> constexpr
1829_LIBCPP_INLINE_VISIBILITY
1830auto data(_Cont& __c)
1831_NOEXCEPT_(noexcept(__c.data()))
1832-> decltype        (__c.data())
1833{ return            __c.data(); }
1834
1835template <class _Cont> constexpr
1836_LIBCPP_INLINE_VISIBILITY
1837auto data(const _Cont& __c)
1838_NOEXCEPT_(noexcept(__c.data()))
1839-> decltype        (__c.data())
1840{ return            __c.data(); }
1841
1842template <class _Tp, size_t _Sz>
1843_LIBCPP_INLINE_VISIBILITY
1844constexpr _Tp* data(_Tp (&__array)[_Sz]) noexcept { return __array; }
1845
1846template <class _Ep>
1847_LIBCPP_INLINE_VISIBILITY
1848constexpr const _Ep* data(initializer_list<_Ep> __il) noexcept { return __il.begin(); }
1849#endif
1850
1851template <class _Container, class _Predicate>
1852typename _Container::size_type
1853__libcpp_erase_if_container(_Container& __c, _Predicate& __pred) {
1854  typename _Container::size_type __old_size = __c.size();
1855
1856  const typename _Container::iterator __last = __c.end();
1857  for (typename _Container::iterator __iter = __c.begin(); __iter != __last;) {
1858    if (__pred(*__iter))
1859      __iter = __c.erase(__iter);
1860    else
1861      ++__iter;
1862  }
1863
1864  return __old_size - __c.size();
1865}
1866
1867_LIBCPP_END_NAMESPACE_STD
1868
1869#endif // _LIBCPP_ITERATOR
1870