[sequences] (original) (raw)
23 Containers library [containers]
23.3 Sequence containers [sequences]
23.3.1 General [sequences.general]
The headers,,,,,, anddefine class templates that meet the requirements for sequence containers.
The following exposition-only alias template may appear in deduction guides for sequence containers:template<class InputIterator> using iter-value-type = typename iterator_traits<InputIterator>::value_type;
23.3.3 Class template array [array]
23.3.3.1 Overview [array.overview]
The header defines a class template for storing fixed-size sequences of objects.
An instance of array<T, N> stores N elements of type T, so that size() == N is an invariant.
An array is an aggregate that can be list-initialized with up to N elements whose types are convertible to T.
An array meets all of the requirements of a container ([container.reqmts]) and of a reversible container ([container.rev.reqmts]), except that a default constructed array object is not empty if .
Descriptions are provided here only for operations on array that are not described in one of these tables and for operations where there is additional semantic information.
array<T, N> is a structural type ([temp.param]) ifT is a structural type.
Two values a1 and a2 of type array<T, N>are template-argument-equivalent if and only if each pair of corresponding elements in a1 and a2are template-argument-equivalent.
namespace std { template<class T, size_t N> struct array { using value_type = T;using pointer = T*;using const_pointer = const T*;using reference = T&;using const_reference = const T&;using size_type = size_t;using difference_type = ptrdiff_t;using iterator = implementation-defined; using const_iterator = implementation-defined; using reverse_iterator = std::reverse_iterator<iterator>;using const_reverse_iterator = std::reverse_iterator<const_iterator>;constexpr void fill(const T& u);constexpr void swap(array&) noexcept(is_nothrow_swappable_v<T>);constexpr iterator begin() noexcept;constexpr const_iterator begin() const noexcept;constexpr iterator end() noexcept;constexpr const_iterator end() const noexcept;constexpr reverse_iterator rbegin() noexcept;constexpr const_reverse_iterator rbegin() const noexcept;constexpr reverse_iterator rend() noexcept;constexpr const_reverse_iterator rend() const noexcept;constexpr const_iterator cbegin() const noexcept;constexpr const_iterator cend() const noexcept;constexpr const_reverse_iterator crbegin() const noexcept;constexpr const_reverse_iterator crend() const noexcept;constexpr bool empty() const noexcept;constexpr size_type size() const noexcept;constexpr size_type max_size() const noexcept;constexpr reference operator[](size_type n);constexpr const_reference operator[](size_type n) const;constexpr reference at(size_type n); constexpr const_reference at(size_type n) const; constexpr reference front();constexpr const_reference front() const;constexpr reference back();constexpr const_reference back() const;constexpr T* data() noexcept;constexpr const T* data() const noexcept;};template<class T, class... U> array(T, U...) -> array<T, 1 + sizeof...(U)>;}
23.3.3.2 Constructors, copy, and assignment [array.cons]
In addition to the requirements specified in the container requirements table, the implicitly-declared move constructor and move assignment operator for arrayrequire that T be Cpp17MoveConstructible or Cpp17MoveAssignable, respectively.
template<class T, class... U> array(T, U...) -> array<T, 1 + sizeof...(U)>;
Mandates: (is_same_v<T, U> && ...) is true.
23.3.3.3 Member functions [array.members]
constexpr size_type size() const noexcept;
constexpr T* data() noexcept;constexpr const T* data() const noexcept;
Returns: A pointer such that [data(), data() + size()) is a valid range.
For a non-empty array, data() == addressof(front()) is true.
constexpr void fill(const T& u);
Effects: As if by fill_n(begin(), N, u).
constexpr void swap(array& y) noexcept(is_nothrow_swappable_v<T>);
Effects: Equivalent to swap_ranges(begin(), end(), y.begin()).
[Note 1:
Unlike the swap function for other containers, array::swaptakes linear time, can exit via an exception, and does not cause iterators to become associated with the other container.
— _end note_]
23.3.3.4 Specialized algorithms [array.special]
template<class T, size_t N> constexpr void swap(array<T, N>& x, array<T, N>& y) noexcept(noexcept(x.swap(y)));
Constraints: N == 0 or is_swappable_v<T> is true.
Effects: As if by x.swap(y).
23.3.3.5 Zero-sized arrays [array.zero]
array shall provide support for the special case N == 0.
In the case that N == 0, begin() == end() == unique value.
The return value of data() is unspecified.
The effect of calling front() or back() for a zero-sized array is undefined.
Member function swap() shall have a non-throwing exception specification.
23.3.3.6 Array creation functions [array.creation]
template<class T, size_t N> constexpr array<remove_cv_t<T>, N> to_array(T (&a)[N]);
Mandates: is_array_v<T> is false andis_constructible_v<remove_cv_t<T>, T&> is true.
Preconditions: T meets the Cpp17CopyConstructible requirements.
Returns: {{ a[0], …, a[N - 1] }}.
template<class T, size_t N> constexpr array<remove_cv_t<T>, N> to_array(T (&&a)[N]);
Mandates: is_array_v<T> is false andis_constructible_v<remove_cv_t<T>, T> is true.
Preconditions: T meets the Cpp17MoveConstructible requirements.
Returns: {{ std::move(a[0]), …, std::move(a[N - 1]) }}.
23.3.3.7 Tuple interface [array.tuple]
template<class T, size_t N> struct tuple_size<array<T, N>> : integral_constant<size_t, N> { };
template<size_t I, class T, size_t N> struct tuple_element<I, array<T, N>> { using type = T;};
template<size_t I, class T, size_t N> constexpr T& get(array<T, N>& a) noexcept;template<size_t I, class T, size_t N> constexpr T&& get(array<T, N>&& a) noexcept;template<size_t I, class T, size_t N> constexpr const T& get(const array<T, N>& a) noexcept;template<size_t I, class T, size_t N> constexpr const T&& get(const array<T, N>&& a) noexcept;
Returns: A reference to the element of a, where indexing is zero-based.
23.3.5 Class template deque [deque]
23.3.5.1 Overview [deque.overview]
In addition, it supports constant time insert and erase operations at the beginning or the end; insert and erase in the middle take linear time.
That is, a deque is especially optimized for pushing and popping elements at the beginning and end.
Storage management is handled automatically.
Descriptions are provided here only for operations ondequethat are not described in one of these tables or for operations where there is additional semantic information.
namespace std { template<class T, class Allocator = allocator<T>> class deque { public: using value_type = T;using allocator_type = Allocator;using pointer = typename allocator_traits<Allocator>::pointer;using const_pointer = typename allocator_traits<Allocator>::const_pointer;using reference = value_type&;using const_reference = const value_type&;using size_type = implementation-defined; using difference_type = implementation-defined; using iterator = implementation-defined; using const_iterator = implementation-defined; using reverse_iterator = std::reverse_iterator<iterator>;using const_reverse_iterator = std::reverse_iterator<const_iterator>;constexpr deque() : deque(Allocator()) { } constexpr explicit deque(const Allocator&);constexpr explicit deque(size_type n, const Allocator& = Allocator());constexpr deque(size_type n, const T& value, const Allocator& = Allocator());template<class InputIterator> constexpr deque(InputIterator first, InputIterator last, const Allocator& = Allocator());template<container-compatible-range<T> R> constexpr deque(from_range_t, R&& rg, const Allocator& = Allocator());constexpr deque(const deque& x);constexpr deque(deque&&);constexpr deque(const deque&, const type_identity_t<Allocator>&);constexpr deque(deque&&, const type_identity_t<Allocator>&);constexpr deque(initializer_list<T>, const Allocator& = Allocator());constexpr ~deque();constexpr deque& operator=(const deque& x);constexpr deque& operator=(deque&& x) noexcept(allocator_traits<Allocator>::is_always_equal::value);constexpr deque& operator=(initializer_list<T>);template<class InputIterator> constexpr void assign(InputIterator first, InputIterator last);template<container-compatible-range<T> R> constexpr void assign_range(R&& rg);constexpr void assign(size_type n, const T& t);constexpr void assign(initializer_list<T>);constexpr allocator_type get_allocator() const noexcept;constexpr iterator begin() noexcept;constexpr const_iterator begin() const noexcept;constexpr iterator end() noexcept;constexpr const_iterator end() const noexcept;constexpr reverse_iterator rbegin() noexcept;constexpr const_reverse_iterator rbegin() const noexcept;constexpr reverse_iterator rend() noexcept;constexpr const_reverse_iterator rend() const noexcept;constexpr const_iterator cbegin() const noexcept;constexpr const_iterator cend() const noexcept;constexpr const_reverse_iterator crbegin() const noexcept;constexpr const_reverse_iterator crend() const noexcept;constexpr bool empty() const noexcept;constexpr size_type size() const noexcept;constexpr size_type max_size() const noexcept;constexpr void resize(size_type sz);constexpr void resize(size_type sz, const T& c);constexpr void shrink_to_fit();constexpr reference operator[](size_type n);constexpr const_reference operator[](size_type n) const;constexpr reference at(size_type n);constexpr const_reference at(size_type n) const;constexpr reference front();constexpr const_reference front() const;constexpr reference back();constexpr const_reference back() const;template<class... Args> constexpr reference emplace_front(Args&&... args);template<class... Args> constexpr reference emplace_back(Args&&... args);template<class... Args> constexpr iterator emplace(const_iterator position, Args&&... args);constexpr void push_front(const T& x);constexpr void push_front(T&& x);template<container-compatible-range<T> R> constexpr void prepend_range(R&& rg);constexpr void push_back(const T& x);constexpr void push_back(T&& x);template<container-compatible-range<T> R> constexpr void append_range(R&& rg);constexpr iterator insert(const_iterator position, const T& x);constexpr iterator insert(const_iterator position, T&& x);constexpr iterator insert(const_iterator position, size_type n, const T& x);template<class InputIterator> constexpr iterator insert(const_iterator position, InputIterator first, InputIterator last);template<container-compatible-range<T> R> constexpr iterator insert_range(const_iterator position, R&& rg);constexpr iterator insert(const_iterator position, initializer_list<T>);constexpr void pop_front();constexpr void pop_back();constexpr iterator erase(const_iterator position);constexpr iterator erase(const_iterator first, const_iterator last);constexpr void swap(deque&) noexcept(allocator_traits<Allocator>::is_always_equal::value);constexpr void clear() noexcept;};template<class InputIterator, class Allocator = allocator<_iter-value-type_<InputIterator>>> deque(InputIterator, InputIterator, Allocator = Allocator()) -> deque<_iter-value-type_<InputIterator>, Allocator>;template<ranges::input_range R, class Allocator = allocator<ranges::range_value_t<R>>> deque(from_range_t, R&&, Allocator = Allocator()) -> deque<ranges::range_value_t<R>, Allocator>;}
23.3.5.2 Constructors, copy, and assignment [deque.cons]
constexpr explicit deque(const Allocator&);
Effects: Constructs an emptydeque, using the specified allocator.
constexpr explicit deque(size_type n, const Allocator& = Allocator());
Preconditions: T is Cpp17DefaultInsertable into deque.
Effects: Constructs a deque withn default-inserted elements using the specified allocator.
constexpr deque(size_type n, const T& value, const Allocator& = Allocator());
Preconditions: T is Cpp17CopyInsertable into deque.
Effects: Constructs adequewith n copies of value, using the specified allocator.
template<class InputIterator> constexpr deque(InputIterator first, InputIterator last, const Allocator& = Allocator());
Effects: Constructs adequeequal to the range [first, last), using the specified allocator.
Complexity: Linear in distance(first, last).
Effects: Constructs a deque with the elements of the range rg, using the specified allocator.
Complexity: Linear in ranges::distance(rg).
23.3.5.3 Capacity [deque.capacity]
constexpr void resize(size_type sz);
Preconditions: T is Cpp17MoveInsertable and Cpp17DefaultInsertable into deque.
Effects: If sz < size(), erases the last size() - sz elements from the sequence.
Otherwise, appends sz - size() default-inserted elements to the sequence.
constexpr void resize(size_type sz, const T& c);
Preconditions: T is Cpp17CopyInsertable into deque.
Effects: If sz < size(), erases the last size() - sz elements from the sequence.
Otherwise, appends sz - size() copies of c to the sequence.
constexpr void shrink_to_fit();
Preconditions: T is Cpp17MoveInsertable into deque.
Effects: shrink_to_fit is a non-binding request to reduce memory use but does not change the size of the sequence.
[Note 1:
The request is non-binding to allow latitude for implementation-specific optimizations.
— _end note_]
If the size is equal to the old capacity, or if an exception is thrown other than by the move constructor of a non-Cpp17CopyInsertable T, then there are no effects.
Complexity: If the size is not equal to the old capacity, linear in the size of the sequence; otherwise constant.
Remarks: If the size is not equal to the old capacity, then invalidates all the references, pointers, and iterators referring to the elements in the sequence, as well as the past-the-end iterator.
23.3.5.4 Modifiers [deque.modifiers]
constexpr iterator insert(const_iterator position, const T& x);constexpr iterator insert(const_iterator position, T&& x);constexpr iterator insert(const_iterator position, size_type n, const T& x);template<class InputIterator> constexpr iterator insert(const_iterator position, InputIterator first, InputIterator last);template<[_container-compatible-range_](container.intro.reqmts#concept:container-compatible-range "23.2.2.1 Introduction [container.intro.reqmts]")<T> R> constexpr iterator insert_range(const_iterator position, R&& rg);constexpr iterator insert(const_iterator position, initializer_list<T>);template<class... Args> constexpr reference emplace_front(Args&&... args);template<class... Args> constexpr reference emplace_back(Args&&... args);template<class... Args> constexpr iterator emplace(const_iterator position, Args&&... args);constexpr void push_front(const T& x);constexpr void push_front(T&& x);template<[_container-compatible-range_](container.intro.reqmts#concept:container-compatible-range "23.2.2.1 Introduction [container.intro.reqmts]")<T> R> constexpr void prepend_range(R&& rg);constexpr void push_back(const T& x);constexpr void push_back(T&& x);template<[_container-compatible-range_](container.intro.reqmts#concept:container-compatible-range "23.2.2.1 Introduction [container.intro.reqmts]")<T> R> constexpr void append_range(R&& rg);
Effects: An insertion in the middle of the deque invalidates all the iterators and references to elements of the deque.
An insertion at either end of the deque invalidates all the iterators to the deque, but has no effect on the validity of references to elements of the deque.
Complexity: The complexity is linear in the number of elements inserted plus the lesser of the distances to the beginning and end of the deque.
Inserting a single element at either the beginning or end of a deque always takes constant time and causes a single call to a constructor ofT.
Remarks: If an exception is thrown other than by the copy constructor, move constructor, assignment operator, or move assignment operator ofT, there are no effects.
If an exception is thrown while inserting a single element at either end, there are no effects.
Otherwise, if an exception is thrown by the move constructor of a non-Cpp17CopyInsertable T, the effects are unspecified.
constexpr iterator erase(const_iterator position);constexpr iterator erase(const_iterator first, const_iterator last);constexpr void pop_front();constexpr void pop_back();
Effects: An erase operation that erases the last element of a deque invalidates only the past-the-end iterator and all iterators and references to the erased elements.
An erase operation that erases the first element of a deque but not the last element invalidates only iterators and references to the erased elements.
An erase operation that erases neither the first element nor the last element of a deque invalidates the past-the-end iterator and all iterators and references to all the elements of the deque.
[Note 1:
pop_front and pop_back are erase operations.
— _end note_]
Throws: Nothing unless an exception is thrown by the assignment operator ofT.
Complexity: The number of calls to the destructor of T is the same as the number of elements erased, but the number of calls to the assignment operator of T is no more than the lesser of the number of elements before the erased elements and the number of elements after the erased elements.
23.3.5.5 Erasure [deque.erasure]
template<class T, class Allocator, class U = T> constexpr typename deque<T, Allocator>::size_type erase(deque<T, Allocator>& c, const U& value);
Effects: Equivalent to:auto it = remove(c.begin(), c.end(), value);auto r = distance(it, c.end()); c.erase(it, c.end());return r;
template<class T, class Allocator, class Predicate> constexpr typename deque<T, Allocator>::size_type erase_if(deque<T, Allocator>& c, Predicate pred);
Effects: Equivalent to:auto it = remove_if(c.begin(), c.end(), pred);auto r = distance(it, c.end()); c.erase(it, c.end());return r;
23.3.7 Class template forward_list [forward.list]
23.3.7.1 Overview [forward.list.overview]
A forward_list is a container that supports forward iterators and allows constant time insert and erase operations anywhere within the sequence, with storage management handled automatically.
Fast random access to list elements is not supported.
[Note 1:
It is intended that forward_list have zero space or time overhead relative to a hand-written C-style singly linked list.
Features that would conflict with that goal have been omitted.
— _end note_]
A forward_list meets all of the requirements of a container ([container.reqmts]), except that the size() member function is not provided andoperator== has linear complexity.
A forward_list also meets all of the requirements for an allocator-aware container ([container.alloc.reqmts]).
In addition, a forward_listprovides the assign member functions and several of the optional sequence container requirements ([sequence.reqmts]).
Descriptions are provided here only for operations onforward_list that are not described in that table or for operations where there is additional semantic information.
[Note 2:
Modifying any list requires access to the element preceding the first element of interest, but in a forward_list there is no constant-time way to access a preceding element.
For this reason, erase_after and splice_aftertake fully-open ranges, not semi-open ranges.
— _end note_]
namespace std { template<class T, class Allocator = allocator<T>> class forward_list { public: using value_type = T;using allocator_type = Allocator;using pointer = typename allocator_traits<Allocator>::pointer;using const_pointer = typename allocator_traits<Allocator>::const_pointer;using reference = value_type&;using const_reference = const value_type&;using size_type = implementation-defined; using difference_type = implementation-defined; using iterator = implementation-defined; using const_iterator = implementation-defined; constexpr forward_list() : forward_list(Allocator()) { } constexpr explicit forward_list(const Allocator&);constexpr explicit forward_list(size_type n, const Allocator& = Allocator());constexpr forward_list(size_type n, const T& value, const Allocator& = Allocator());template<class InputIterator> constexpr forward_list(InputIterator first, InputIterator last,const Allocator& = Allocator());template<container-compatible-range<T> R> constexpr forward_list(from_range_t, R&& rg, const Allocator& = Allocator());constexpr forward_list(const forward_list& x);constexpr forward_list(forward_list&& x);constexpr forward_list(const forward_list& x, const type_identity_t<Allocator>&);constexpr forward_list(forward_list&& x, const type_identity_t<Allocator>&);constexpr forward_list(initializer_list<T>, const Allocator& = Allocator());constexpr ~forward_list();constexpr forward_list& operator=(const forward_list& x);constexpr forward_list& operator=(forward_list&& x) noexcept(allocator_traits<Allocator>::is_always_equal::value);constexpr forward_list& operator=(initializer_list<T>);template<class InputIterator> constexpr void assign(InputIterator first, InputIterator last);template<container-compatible-range<T> R> constexpr void assign_range(R&& rg);constexpr void assign(size_type n, const T& t);constexpr void assign(initializer_list<T>);constexpr allocator_type get_allocator() const noexcept;constexpr iterator before_begin() noexcept;constexpr const_iterator before_begin() const noexcept;constexpr iterator begin() noexcept;constexpr const_iterator begin() const noexcept;constexpr iterator end() noexcept;constexpr const_iterator end() const noexcept;constexpr const_iterator cbegin() const noexcept;constexpr const_iterator cbefore_begin() const noexcept;constexpr const_iterator cend() const noexcept;constexpr bool empty() const noexcept;constexpr size_type max_size() const noexcept;constexpr reference front();constexpr const_reference front() const;template<class... Args> constexpr reference emplace_front(Args&&... args);constexpr void push_front(const T& x);constexpr void push_front(T&& x);template<container-compatible-range<T> R> constexpr void prepend_range(R&& rg);constexpr void pop_front();template<class... Args> constexpr iterator emplace_after(const_iterator position, Args&&... args);constexpr iterator insert_after(const_iterator position, const T& x);constexpr iterator insert_after(const_iterator position, T&& x);constexpr iterator insert_after(const_iterator position, size_type n, const T& x);template<class InputIterator> constexpr iterator insert_after(const_iterator position, InputIterator first, InputIterator last);constexpr iterator insert_after(const_iterator position, initializer_list<T> il);template<container-compatible-range<T> R> constexpr iterator insert_range_after(const_iterator position, R&& rg);constexpr iterator erase_after(const_iterator position);constexpr iterator erase_after(const_iterator position, const_iterator last);constexpr void swap(forward_list&) noexcept(allocator_traits<Allocator>::is_always_equal::value);constexpr void resize(size_type sz);constexpr void resize(size_type sz, const value_type& c);constexpr void clear() noexcept;constexpr void splice_after(const_iterator position, forward_list& x);constexpr void splice_after(const_iterator position, forward_list&& x);constexpr void splice_after(const_iterator position, forward_list& x, const_iterator i);constexpr void splice_after(const_iterator position, forward_list&& x, const_iterator i);constexpr void splice_after(const_iterator position, forward_list& x, const_iterator first, const_iterator last);constexpr void splice_after(const_iterator position, forward_list&& x, const_iterator first, const_iterator last);constexpr size_type remove(const T& value);template<class Predicate> constexpr size_type remove_if(Predicate pred); size_type unique();template<class BinaryPredicate> constexpr size_type unique(BinaryPredicate binary_pred);constexpr void merge(forward_list& x);constexpr void merge(forward_list&& x);template<class Compare> constexpr void merge(forward_list& x, Compare comp);template<class Compare> constexpr void merge(forward_list&& x, Compare comp);constexpr void sort();template<class Compare> constexpr void sort(Compare comp);constexpr void reverse() noexcept;};template<class InputIterator, class Allocator = allocator<_iter-value-type_<InputIterator>>> forward_list(InputIterator, InputIterator, Allocator = Allocator()) -> forward_list<_iter-value-type_<InputIterator>, Allocator>;template<ranges::input_range R, class Allocator = allocator<ranges::range_value_t<R>>> forward_list(from_range_t, R&&, Allocator = Allocator()) -> forward_list<ranges::range_value_t<R>, Allocator>;}
T shall be complete before any member of the resulting specialization of forward_list is referenced.
23.3.7.2 Constructors, copy, and assignment [forward.list.cons]
constexpr explicit forward_list(const Allocator&);
Effects: Constructs an empty forward_list object using the specified allocator.
constexpr explicit forward_list(size_type n, const Allocator& = Allocator());
Preconditions: T is Cpp17DefaultInsertable into forward_list.
Effects: Constructs a forward_list object with ndefault-inserted elements using the specified allocator.
constexpr forward_list(size_type n, const T& value, const Allocator& = Allocator());
Preconditions: T is Cpp17CopyInsertable into forward_list.
Effects: Constructs a forward_list object with n copies of value using the specified allocator.
template<class InputIterator> constexpr forward_list(InputIterator first, InputIterator last, const Allocator& = Allocator());
Effects: Constructs a forward_list object equal to the range [first, last).
Complexity: Linear in distance(first, last).
Effects: Constructs a forward_list object with the elements of the range rg.
Complexity: Linear in ranges::distance(rg).
23.3.7.3 Iterators [forward.list.iter]
constexpr iterator before_begin() noexcept;constexpr const_iterator before_begin() const noexcept;constexpr const_iterator cbefore_begin() const noexcept;
Effects: cbefore_begin() is equivalent toconst_cast<forward_list const&>(*this).before_begin().
Returns: A non-dereferenceable iterator that, when incremented, is equal to the iterator returned by begin().
Remarks: before_begin() == end() shall equal false.
23.3.7.5 Modifiers [forward.list.modifiers]
The member functions in this subclause do not affect the validity of iterators and references when inserting elements, and when erasing elements invalidate iterators and references to the erased elements only.
If an exception is thrown by any of these member functions there is no effect on the container.
Inserting n elements into a forward_list is linear inn, and the number of calls to the copy or move constructor of T is exactly equal to n.
Erasing n elements from a forward_list is linear in n and the number of calls to the destructor of type T is exactly equal to n.
template<class... Args> constexpr reference emplace_front(Args&&... args);
Effects: Inserts an object of type value_type constructed withvalue_type(std::forward<Args>(args)...) at the beginning of the list.
constexpr void push_front(const T& x);constexpr void push_front(T&& x);
Effects: Inserts a copy of x at the beginning of the list.
Effects: Inserts a copy of each element of rg at the beginning of the list.
[Note 1:
The order of elements is not reversed.
— _end note_]
constexpr void pop_front();
Effects: As if by erase_after(before_begin()).
constexpr iterator insert_after(const_iterator position, const T& x);
Preconditions: T is Cpp17CopyInsertable into forward_list.
position is before_begin() or is a dereferenceable iterator in the range [begin(), end()).
Effects: Inserts a copy of x after position.
Returns: An iterator pointing to the copy of x.
constexpr iterator insert_after(const_iterator position, T&& x);
Preconditions: T is Cpp17MoveInsertable into forward_list.
position is before_begin() or is a dereferenceable iterator in the range [begin(), end()).
Effects: Inserts a copy of x after position.
Returns: An iterator pointing to the copy of x.
constexpr iterator insert_after(const_iterator position, size_type n, const T& x);
Preconditions: T is Cpp17CopyInsertable into forward_list.
position is before_begin() or is a dereferenceable iterator in the range [begin(), end()).
Effects: Inserts n copies of x after position.
Returns: An iterator pointing to the last inserted copy of x, orposition if n == 0 is true.
template<class InputIterator> constexpr iterator insert_after(const_iterator position, InputIterator first, InputIterator last);
Preconditions: T is Cpp17EmplaceConstructible into forward_listfrom *first.
position is before_begin() or is a dereferenceable iterator in the range [begin(), end()).
Neither first nor last are iterators in *this.
Effects: Inserts copies of elements in [first, last) after position.
Returns: An iterator pointing to the last inserted element, orposition if first == last is true.
Preconditions: T is Cpp17EmplaceConstructible into forward_listfrom *ranges::begin(rg).
position is before_begin() or is a dereferenceable iterator in the range [begin(), end()).
rg and *this do not overlap.
Effects: Inserts copies of elements in the range rg after position.
Returns: An iterator pointing to the last inserted element, or position if rg is empty.
constexpr iterator insert_after(const_iterator position, initializer_list<T> il);
Effects: Equivalent to: return insert_after(position, il.begin(), il.end());
template<class... Args> constexpr iterator emplace_after(const_iterator position, Args&&... args);
Preconditions: T is Cpp17EmplaceConstructible into forward_listfrom std::forward<Args>(args)....
position is before_begin() or is a dereferenceable iterator in the range [begin(), end()).
Effects: Inserts an object of type value_type direct-non-list-initialized withstd::forward<Args>(args)... after position.
Returns: An iterator pointing to the new object.
constexpr iterator erase_after(const_iterator position);
Preconditions: The iterator following position is dereferenceable.
Effects: Erases the element pointed to by the iterator following position.
Returns: An iterator pointing to the element following the one that was erased, or end() if no such element exists.
constexpr iterator erase_after(const_iterator position, const_iterator last);
Preconditions: All iterators in the range (position, last) are dereferenceable.
Effects: Erases the elements in the range (position, last).
constexpr void resize(size_type sz);
Preconditions: T is Cpp17DefaultInsertable into forward_list.
Effects: If sz < distance(begin(), end()), erases the last distance(begin(), end()) - sz elements from the list.
Otherwise, inserts sz - distance(begin(), end()) default-inserted elements at the end of the list.
constexpr void resize(size_type sz, const value_type& c);
Preconditions: T is Cpp17CopyInsertable into forward_list.
Effects: If sz < distance(begin(), end()), erases the last distance(begin(), end()) - sz elements from the list.
Otherwise, inserts sz - distance(begin(), end())copies of c at the end of the list.
constexpr void clear() noexcept;
Effects: Erases all elements in the range [begin(), end()).
Remarks: Does not invalidate past-the-end iterators.
23.3.7.6 Operations [forward.list.ops]
In this subclause, arguments for a template parameter named Predicate or BinaryPredicateshall meet the corresponding requirements in [algorithms.requirements].
The semantics of i + n, where i is an iterator into the list and n is an integer, are the same as those of next(i, n).
The expression i - n, where i is an iterator into the list and n is an integer, means an iterator j such that j + n == i is true.
For merge and sort, the definitions and requirements in [alg.sorting] apply.
constexpr void splice_after(const_iterator position, forward_list& x);constexpr void splice_after(const_iterator position, forward_list&& x);
Preconditions: position is before_begin() or is a dereferenceable iterator in the range [begin(), end()).
get_allocator() == x.get_allocator() is true.
addressof(x) != this is true.
Effects: Inserts the contents of x afterposition, and x becomes empty.
Pointers and references to the moved elements of x now refer to those same elements but as members of *this.
Iterators referring to the moved elements will continue to refer to their elements, but they now behave as iterators into *this, not into x.
constexpr void splice_after(const_iterator position, forward_list& x, const_iterator i);constexpr void splice_after(const_iterator position, forward_list&& x, const_iterator i);
Preconditions: position is before_begin() or is a dereferenceable iterator in the range [begin(), end()).
The iterator following i is a dereferenceable iterator in x.
get_allocator() == x.get_allocator() is true.
Effects: Inserts the element following i into *this, followingposition, and removes it from x.
The result is unchanged if position == i or position == ++i.
Pointers and references to *++i continue to refer to the same element but as a member of*this.
Iterators to *++i continue to refer to the same element, but now behave as iterators into *this, not into x.
constexpr void splice_after(const_iterator position, forward_list& x, const_iterator first, const_iterator last);constexpr void splice_after(const_iterator position, forward_list&& x, const_iterator first, const_iterator last);
Preconditions: position is before_begin() or is a dereferenceable iterator in the range [begin(), end()).
(first, last) is a valid range in x, and all iterators in the range (first, last) are dereferenceable.
position is not an iterator in the range (first, last).
get_allocator() == x.get_allocator() is true.
Effects: Inserts elements in the range (first, last) after position and removes the elements from x.
Pointers and references to the moved elements ofx now refer to those same elements but as members of *this.
Iterators referring to the moved elements will continue to refer to their elements, but they now behave as iterators into *this, not into x.
constexpr size_type remove(const T& value);template<class Predicate> constexpr size_type remove_if(Predicate pred);
Effects: Erases all the elements in the list referred to by a list iterator i for which the following conditions hold: *i == value (for remove()),pred(*i) is true (for remove_if()).
Invalidates only the iterators and references to the erased elements.
Returns: The number of elements erased.
Throws: Nothing unless an exception is thrown by the equality comparison or the predicate.
Complexity: Exactly distance(begin(), end()) applications of the corresponding predicate.
constexpr size_type unique();template<class BinaryPredicate> constexpr size_type unique(BinaryPredicate binary_pred);
Let binary_pred be equal_to<>{} for the first overload.
Preconditions: binary_pred is an equivalence relation.
Effects: Erases all but the first element from every consecutive group of equivalent elements.
That is, for a nonempty list, erases all elements referred to by the iterator i in the range [begin() + 1, end()) for which binary_pred(*i, *(i - 1)) is true.
Invalidates only the iterators and references to the erased elements.
Returns: The number of elements erased.
Throws: Nothing unless an exception is thrown by the predicate.
Complexity: If empty() is false, exactly distance(begin(), end()) - 1 applications of the corresponding predicate, otherwise no applications of the predicate.
constexpr void merge(forward_list& x);constexpr void merge(forward_list&& x);template<class Compare> constexpr void merge(forward_list& x, Compare comp);template<class Compare> constexpr void merge(forward_list&& x, Compare comp);
Let comp be less<> for the first two overloads.
Preconditions: *this and x are both sorted with respect to the comparator comp, andget_allocator() == x.get_allocator() is true.
Effects: If addressof(x) == this, there are no effects.
Otherwise, merges the two sorted ranges [begin(), end()) and [x.begin(), x.end()).
The result is a range that is sorted with respect to the comparator comp.
Pointers and references to the moved elements of x now refer to those same elements but as members of *this.
Iterators referring to the moved elements will continue to refer to their elements, but they now behave as iterators into *this, not intox.
Complexity: At most distance(begin(), end()) + distance(x.begin(), x.end()) - 1 comparisons if addressof(x) != this; otherwise, no comparisons are performed.
If addressof(x) != this, x is empty after the merge.
No elements are copied by this operation.
If an exception is thrown other than by a comparison, there are no effects.
constexpr void sort();template<class Compare> constexpr void sort(Compare comp);
Effects: Sorts the list according to the operator< or the comp function object.
If an exception is thrown, the order of the elements in *this is unspecified.
Does not affect the validity of iterators and references.
Complexity: Approximately comparisons, where N is distance(begin(), end()).
constexpr void reverse() noexcept;
Effects: Reverses the order of the elements in the list.
Does not affect the validity of iterators and references.
23.3.7.7 Erasure [forward.list.erasure]
template<class T, class Allocator, class U = T> constexpr typename forward_list<T, Allocator>::size_type erase(forward_list<T, Allocator>& c, const U& value);
Effects: Equivalent to: return erase_if(c, [&](const auto& elem) -> bool { return elem == value; });
template<class T, class Allocator, class Predicate> constexpr typename forward_list<T, Allocator>::size_type erase_if(forward_list<T, Allocator>& c, Predicate pred);
Effects: Equivalent to: return c.remove_if(pred);
23.3.9 Class template hive [hive]
23.3.9.1 Overview [hive.overview]
A hive is a type of sequence container that provides constant-time insertion and erasure operations.
Storage is automatically managed in multiple memory blocks, referred to as element blocks.
Insertion position is determined by the container, and insertion may re-use the memory locations of erased elements.
Element blocks which contain elements are referred to as active blocks, those which do not are referred to as reserved blocks.
Active blocks which become empty of elements are either deallocated or become reserved blocks.
Reserved blocks become active blocks when they are used to store elements.
A user can create additional reserved blocks by calling reserve.
Erasures use unspecified techniques of constant time complexity to identify the memory locations of erased elements, which are subsequently skipped during iteration, as opposed to relocating subsequent elements during erasure.
Active block capacities have an implementation-defined growth factor (which need not be integral), for example a new active block's capacity could be equal to the summed capacities of the pre-existing active blocks.
Limits can be placed on both the minimum and maximum element capacities of element blocks, both by users and implementations.
- The minimum limit shall be no larger than the maximum limit.
- When limits are not specified by a user during construction, the implementation's default limits are used.
- The default limits of an implementation are not guaranteed to be the same as the minimum and maximum possible capacities for an implementation's element blocks.
[Note 1:
To allow latitude for both implementation-specific and user-directed optimization.
— _end note_]
The latter are defined as hard limits.
The maximum hard limit shall be no larger thanstd::allocator_traits<Allocator>::max_size(). - If user-specified limits are not within hard limits, or if the specified minimum limit is greater than the specified maximum limit, the behavior is undefined.
- An element block is said to be within the boundsof a pair of minimum/maximum limits when its capacity is greater-or-equal-to the minimum limit and less-than-or-equal-to the maximum limit.
A hive conforms to the requirements for containers ([container.reqmts]), with the exception of operators == and !=.
Descriptions are provided here only for operations on hivethat are not described in that table or for operations where there is additional semantic information.
The iterators of hive meet the Cpp17BidirectionalIterator requirements but also model three_way_comparable<strong_ordering>.
namespace std { template<class T, class Allocator = allocator<T>> class hive { public: using value_type = T;using allocator_type = Allocator;using pointer = typename allocator_traits<Allocator>::pointer;using const_pointer = typename allocator_traits<Allocator>::const_pointer;using reference = value_type&;using const_reference = const value_type&;using size_type = implementation-defined; using difference_type = implementation-defined; using iterator = implementation-defined; using const_iterator = implementation-defined; using reverse_iterator = std::reverse_iterator<iterator>; using const_reverse_iterator = std::reverse_iterator<const_iterator>; constexpr hive() noexcept(noexcept(Allocator())) : hive(Allocator()) {} constexpr explicit hive(const Allocator&) noexcept;constexpr explicit hive(hive_limits block_limits) : hive(block_limits, Allocator()) {} constexpr hive(hive_limits block_limits, const Allocator&);explicit hive(size_type n, const Allocator& = Allocator()); hive(size_type n, hive_limits block_limits, const Allocator& = Allocator()); hive(size_type n, const T& value, const Allocator& = Allocator()); hive(size_type n, const T& value, hive_limits block_limits, const Allocator& = Allocator());template<class InputIterator> hive(InputIterator first, InputIterator last, const Allocator& = Allocator());template<class InputIterator> hive(InputIterator first, InputIterator last, hive_limits block_limits,const Allocator& = Allocator());template<container-compatible-range<T> R> hive(from_range_t, R&& rg, const Allocator& = Allocator());template<container-compatible-range<T> R> hive(from_range_t, R&& rg, hive_limits block_limits, const Allocator& = Allocator()); hive(const hive& x); hive(hive&&) noexcept; hive(const hive& x, const type_identity_t<Allocator>& alloc); hive(hive&&, const type_identity_t<Allocator>& alloc); hive(initializer_list<T> il, const Allocator& = Allocator()); hive(initializer_list<T> il, hive_limits block_limits, const Allocator& = Allocator());~hive(); hive& operator=(const hive& x); hive& operator=(hive&& x) noexcept(see below); hive& operator=(initializer_list<T>);template<class InputIterator> void assign(InputIterator first, InputIterator last);template<container-compatible-range<T> R> void assign_range(R&& rg);void assign(size_type n, const T& t);void assign(initializer_list<T>); allocator_type get_allocator() const noexcept; iterator begin() noexcept; const_iterator begin() const noexcept; iterator end() noexcept; const_iterator end() const noexcept; reverse_iterator rbegin() noexcept; const_reverse_iterator rbegin() const noexcept; reverse_iterator rend() noexcept; const_reverse_iterator rend() const noexcept; const_iterator cbegin() const noexcept; const_iterator cend() const noexcept; const_reverse_iterator crbegin() const noexcept; const_reverse_iterator crend() const noexcept;bool empty() const noexcept; size_type size() const noexcept; size_type max_size() const noexcept; size_type capacity() const noexcept;void reserve(size_type n);void shrink_to_fit();void trim_capacity() noexcept;void trim_capacity(size_type n) noexcept;constexpr hive_limits block_capacity_limits() const noexcept;static constexpr hive_limits block_capacity_default_limits() noexcept;static constexpr hive_limits block_capacity_hard_limits() noexcept;void reshape(hive_limits block_limits);template<class... Args> iterator emplace(Args&&... args);template<class... Args> iterator emplace_hint(const_iterator hint, Args&&... args); iterator insert(const T& x); iterator insert(T&& x); iterator insert(const_iterator hint, const T& x); iterator insert(const_iterator hint, T&& x);void insert(initializer_list<T> il);template<container-compatible-range<T> R> void insert_range(R&& rg);template<class InputIterator> void insert(InputIterator first, InputIterator last);void insert(size_type n, const T& x); iterator erase(const_iterator position); iterator erase(const_iterator first, const_iterator last);void swap(hive&) noexcept(see below);void clear() noexcept;void splice(hive& x);void splice(hive&& x);template<class BinaryPredicate = equal_to<T>> size_type unique(BinaryPredicate binary_pred = BinaryPredicate());template<class Compare = less<T>> void sort(Compare comp = Compare()); iterator get_iterator(const_pointer p) noexcept; const_iterator get_iterator(const_pointer p) const noexcept;private: hive_limits current-limits = implementation-defined; };template<class InputIterator, class Allocator = allocator<_iter-value-type_<InputIterator>>> hive(InputIterator, InputIterator, Allocator = Allocator()) -> hive<_iter-value-type_<InputIterator>, Allocator>;template<class InputIterator, class Allocator = allocator<_iter-value-type_<InputIterator>>> hive(InputIterator, InputIterator, hive_limits, Allocator = Allocator()) -> hive<_iter-value-type_<InputIterator>, Allocator>;template<ranges::input_range R, class Allocator = allocator<ranges::range_value_t<R>>> hive(from_range_t, R&&, Allocator = Allocator()) -> hive<ranges::range_value_t<R>, Allocator>;template<ranges::input_range R, class Allocator = allocator<ranges::range_value_t<R>>> hive(from_range_t, R&&, hive_limits, Allocator = Allocator()) -> hive<ranges::range_value_t<R>, Allocator>;}
23.3.9.2 Constructors, copy, and assignment [hive.cons]
constexpr explicit hive(const Allocator&) noexcept;
Effects: Constructs an empty hive, using the specified allocator.
constexpr hive(hive_limits block_limits, const Allocator&);
Effects: Constructs an empty hive, using the specified allocator.
Initializes current-limits with block_limits.
explicit hive(size_type n, const Allocator& = Allocator()); hive(size_type n, hive_limits block_limits, const Allocator& = Allocator());
Preconditions: T is Cpp17DefaultInsertable into hive.
Effects: Constructs a hive with n default-inserted elements, using the specified allocator.
If the second overload is called, also initializes current-limits with block_limits.
hive(size_type n, const T& value, const Allocator& = Allocator()); hive(size_type n, const T& value, hive_limits block_limits, const Allocator& = Allocator());
Preconditions: T is Cpp17CopyInsertable into hive.
Effects: Constructs a hive with n copies of value, using the specified allocator.
If the second overload is called, also initializes current-limits with block_limits.
template<class InputIterator> hive(InputIterator first, InputIterator last, const Allocator& = Allocator());template<class InputIterator> hive(InputIterator first, InputIterator last, hive_limits block_limits,const Allocator& = Allocator());
Effects: Constructs a hive equal to the range [first, last), using the specified allocator.
If the second overload is called, also initializes current-limits with block_limits.
Complexity: Linear in distance(first, last).
Effects: Constructs a hive object with the elements of the range rg, using the specified allocator.
If the second overload is called, also initializes current-limits with block_limits.
Complexity: Linear in ranges::distance(rg).
hive(const hive& x); hive(const hive& x, const type_identity_t<Allocator>& alloc);
Preconditions: T is Cpp17CopyInsertable into hive.
Effects: Constructs a hive object with the elements of x.
If the second overload is called, uses alloc.
Initializes current-limits with x.current-limits.
Complexity: Linear in x.size().
hive(hive&& x); hive(hive&& x, const type_identity_t<Allocator>& alloc);
Preconditions: For the second overload, when allocator_traits<alloc>::is_always_equal::value is false,T meets the Cpp17MoveInsertable requirements.
Effects: When the first overload is called, or the second overload is called andalloc == x.get_allocator() is true,current-limits is set to x.current-limits and each element block is moved from x into *this.
Pointers and references to the elements of x now refer to those same elements but as members of *this.
Iterators referring to the elements of xwill continue to refer to their elements, but they now behave as iterators into *this.
If the second overload is called andalloc == x.get_allocator() is false, each element in x is moved into *this.
References, pointers and iterators referring to the elements of x, as well as the past-the-end iterator of x, are invalidated.
Postconditions: x.empty() is true.
Complexity: If the second overload is called andalloc == x.get_allocator() is false, linear in x.size().
Otherwise constant.
hive(initializer_list<T> il, const Allocator& = Allocator()); hive(initializer_list<T> il, hive_limits block_limits, const Allocator& = Allocator());
Preconditions: T is Cpp17CopyInsertable into hive.
Effects: Constructs a hive object with the elements of il, using the specified allocator.
If the second overload is called, also initializes current-limits with block_limits.
Complexity: Linear in il.size().
hive& operator=(const hive& x);
Preconditions: T is Cpp17CopyInsertable into hive and_Cpp17CopyAssignable_.
Effects: All elements in *this are either copy-assigned to, or destroyed.
All elements in x are copied into *this.
[Note 1:
current-limits is unchanged.
— _end note_]
Complexity: Linear in size() + x.size().
hive& operator=(hive&& x) noexcept(allocator_traits<Allocator>::propagate_on_container_move_assignment::value || allocator_traits<Allocator>::is_always_equal::value);
Preconditions: When(allocator_traits<Allocator>::propagate_on_container_move_assignment::value || allocator_traits<Allocator>::is_always_equal::value) is false,T is Cpp17MoveInsertable into hive and_Cpp17MoveAssignable_.
Effects: Each element in *this is either move-assigned to, or destroyed.
When(allocator_traits<Allocator>::propagate_on_container_move_assignment::value || get_allocator() == x.get_allocator()) is true,current-limits is set to x.current-limits and each element block is moved from x into *this.
Pointers and references to the elements of xnow refer to those same elements but as members of *this.
Iterators referring to the elements of xwill continue to refer to their elements, but they now behave as iterators into *this, not into x.
When(allocator_traits<Allocator>::propagate_on_container_move_assignment::value || get_allocator() == x.get_allocator()) is false, each element in x is moved into *this.
References, pointers and iterators referring to the elements of x, as well as the past-the-end iterator of x, are invalidated.
Postconditions: x.empty() is true.
Complexity: Linear in size().
If(allocator_traits<Allocator>::propagate_on_container_move_assignment::value || get_allocator() == x.get_allocator()) is false, also linear in x.size().
23.3.9.3 Capacity [hive.capacity]
size_type capacity() const noexcept;
Returns: The total number of elements that *this can hold without requiring allocation of more element blocks.
void reserve(size_type n);
Effects: If n <= capacity() is true, there are no effects.
Otherwise increases capacity() by allocating reserved blocks.
Postconditions: capacity() >= n is true.
Throws: length_error if n > max_size(), as well as any exceptions thrown by the allocator.
Complexity: It does not change the size of the sequence and takes at most linear time in the number of reserved blocks allocated.
Remarks: All references, pointers, and iterators referring to elements in *this, as well as the past-the-end iterator, remain valid.
Preconditions: T is Cpp17MoveInsertable into hive.
Effects: shrink_to_fit is a non-binding request to reduce capacity() to be closer to size().
[Note 1:
The request is non-binding to allow latitude for implementation-specific optimizations.
— _end note_]
It does not increase capacity(), but may reduce capacity().
It may reallocate elements.
If capacity() is already equal to size(), there are no effects.
If an exception is thrown during allocation of a new element block,capacity() may be reduced and reallocation may occur.
Otherwise if an exception is thrown, the effects are unspecified.
Complexity: If reallocation happens, linear in the size of the sequence.
Remarks: If reallocation happens, the order of the elements in *this may change and all references, pointers, and iterators referring to the elements in *this, as well as the past-the-end iterator, are invalidated.
void trim_capacity() noexcept;void trim_capacity(size_type n) noexcept;
Effects: For the first overload, all reserved blocks are deallocated, andcapacity() is reduced accordingly.
For the second overload, capacity() is reduced to no less than n.
Complexity: Linear in the number of reserved blocks deallocated.
Remarks: All references, pointers, and iterators referring to elements in *this, as well as the past-the-end iterator, remain valid.
constexpr hive_limits block_capacity_limits() const noexcept;
static constexpr hive_limits block_capacity_default_limits() noexcept;
Returns: A hive_limits struct with the min and max members set to the implementation's default limits.
static constexpr hive_limits block_capacity_hard_limits() noexcept;
Returns: A hive_limits struct with the min and max members set to the implementation's hard limits.
void reshape(hive_limits block_limits);
Preconditions: T is Cpp17MoveInsertable into hive.
Effects: For any active blocks not within the bounds of block_limits, the elements within those active blocks are reallocated to new or existing element blocks which are within the bounds.
Any element blocks not within the bounds of block_limitsare deallocated.
If an exception is thrown during allocation of a new element block,capacity() may be reduced, reallocation may occur, and_current-limits_ may be assigned a value other than block_limits.
Otherwise block_limits is assigned to current-limits.
If any other exception is thrown the effects are unspecified.
Postconditions: size() is unchanged.
Complexity: Linear in the number of element blocks in *this.
If reallocation happens, also linear in the number of elements reallocated.
Remarks: This operation may change capacity().
If reallocation happens, the order of the elements in *this may change.
Reallocation invalidates all references, pointers, and iterators referring to the elements in *this, as well as the past-the-end iterator.
[Note 2:
If no reallocation happens, they remain valid.
— _end note_]
23.3.9.4 Modifiers [hive.modifiers]
template<class... Args> iterator emplace(Args&&... args);template<class... Args> iterator emplace_hint(const_iterator hint, Args&&... args);
Preconditions: T is Cpp17EmplaceConstructible into hive from args.
Effects: Inserts an object of type Tconstructed with std::forward<Args>(args)....
The hint parameter is ignored.
If an exception is thrown, there are no effects.
[Note 1:
args can directly or indirectly refer to a value in *this.
— _end note_]
Returns: An iterator that points to the new element.
Complexity: Constant.
Exactly one object of type T is constructed.
Remarks: Invalidates the past-the-end iterator.
iterator insert(const T& x); iterator insert(const_iterator hint, const T& x); iterator insert(T&& x); iterator insert(const_iterator hint, T&& x);
Effects: Equivalent to: return emplace(std::forward<decltype(x)>(x));
[Note 2:
The hint parameter is ignored.
— _end note_]
Preconditions: T is Cpp17EmplaceInsertable into hivefrom *ranges::begin(rg).
rg and *this do not overlap.
Effects: Inserts copies of elements in rg.
Each iterator in the range rg is dereferenced exactly once.
Complexity: Linear in the number of elements inserted.
Exactly one object of type T is constructed for each element inserted.
Remarks: If an element is inserted, invalidates the past-the-end iterator.
void insert(size_type n, const T& x);
Preconditions: T is Cpp17CopyInsertable into hive.
Effects: Inserts n copies of x.
Complexity: Linear in n.
Exactly one object of type T is constructed for each element inserted.
Remarks: If an element is inserted, invalidates the past-the-end iterator.
template<class InputIterator> void insert(InputIterator first, InputIterator last);
Effects: Equivalent to insert_range(ranges::subrange(first, last)).
iterator erase(const_iterator position); iterator erase(const_iterator first, const_iterator last);
Complexity: Linear in the number of elements erased.
Additionally, if any active blocks become empty of elements as a result of the function call, at worst linear in the number of element blocks.
Remarks: Invalidates references, pointers and iterators referring to the erased elements.
An erase operation that erases the last element in *thisalso invalidates the past-the-end iterator.
void swap(hive& x) noexcept(allocator_traits<Allocator>::propagate_on_container_swap::value || allocator_traits<Allocator>::is_always_equal::value);
Effects: Exchanges the contents, capacity(), and _current-limits_of *this with that of x.
23.3.9.5 Operations [hive.operations]
In this subclause, arguments for a template parameter named Predicate or BinaryPredicateshall meet the corresponding requirements in [algorithms.requirements].
The semantics of i + n and i - n, where i is an iterator into the hive and n is an integer, are the same as those of next(i, n) and prev(i, n), respectively.
For sort, the definitions and requirements in [alg.sorting] apply.
void splice(hive& x);void splice(hive&& x);
Preconditions: get_allocator() == x.get_allocator() is true.
Effects: If addressof(x) == this is true, the behavior is erroneous and there are no effects.
Otherwise, inserts the contents of x into *this andx becomes empty.
Pointers and references to the moved elements of xnow refer to those same elements but as members of *this.
Iterators referring to the moved elements continue to refer to their elements, but they now behave as iterators into *this, not into x.
Throws: length_error if any of x's active blocks are not within the bounds of current-limits.
Complexity: Linear in the sum of all element blocks in x plus all element blocks in *this.
Remarks: Reserved blocks in x are not transferred into *this.
If addressof(x) == this is false, invalidates the past-the-end iterator for both x and *this.
template<class BinaryPredicate = equal_to<T>> size_type unique(BinaryPredicate binary_pred = BinaryPredicate());
Preconditions: binary_pred is an equivalence relation.
Effects: Erases all but the first element from every consecutive group of equivalent elements.
That is, for a nonempty hive, erases all elements referred to by the iterator iin the range [begin() + 1, end()) for which binary_pred(*i, *(i - 1)) is true.
Returns: The number of elements erased.
Throws: Nothing unless an exception is thrown by the predicate.
Complexity: If empty() is false, exactly size() - 1 applications of the corresponding predicate, otherwise no applications of the predicate.
Remarks: Invalidates references, pointers, and iterators referring to the erased elements.
If the last element in *this is erased, also invalidates the past-the-end iterator.
template<class Compare = less<T>> void sort(Compare comp = Compare());
Preconditions: T is Cpp17MoveInsertable into hive,Cpp17MoveAssignable, and Cpp17Swappable.
Effects: Sorts *this according to the comp function object.
If an exception is thrown, the order of the elements in *this is unspecified.
Complexity: comparisons, where N is size().
Remarks: May allocate.
References, pointers, and iterators referring to elements in *this, as well as the past-the-end iterator, may be invalidated.
iterator get_iterator(const_pointer p) noexcept; const_iterator get_iterator(const_pointer p) const noexcept;
Preconditions: p points to an element in *this.
Returns: An iterator or const_iteratorpointing to the same element as p.
Complexity: Linear in the number of active blocks in *this.
23.3.9.6 Erasure [hive.erasure]
template<class T, class Allocator, class U> typename hive<T, Allocator>::size_type erase(hive<T, Allocator>& c, const U& value);
Effects: Equivalent to:return erase_if(c, [&](auto& elem) { return elem == value; });
template<class T, class Allocator, class Predicate> typename hive<T, Allocator>::size_type erase_if(hive<T, Allocator>& c, Predicate pred);
Effects: Equivalent to:auto original_size = c.size();for (auto i = c.begin(), last = c.end(); i != last; ) { if (pred(*i)) { i = c.erase(i);} else { ++i;} } return original_size - c.size();
23.3.11 Class template list [list]
23.3.11.1 Overview [list.overview]
Alistis a sequence container that supports bidirectional iterators and allows constant time insert and erase operations anywhere within the sequence, with storage management handled automatically.
Unlike vectors and deques, fast random access to list elements is not supported, but many algorithms only need sequential access anyway.
The exceptions are theoperator[]andatmember functions, which are not provided.196
Descriptions are provided here only for operations onlistthat are not described in one of these tables or for operations where there is additional semantic information.
namespace std { template<class T, class Allocator = allocator<T>> class list { public: using value_type = T;using allocator_type = Allocator;using pointer = typename allocator_traits<Allocator>::pointer;using const_pointer = typename allocator_traits<Allocator>::const_pointer;using reference = value_type&;using const_reference = const value_type&;using size_type = implementation-defined; using difference_type = implementation-defined; using iterator = implementation-defined; using const_iterator = implementation-defined; using reverse_iterator = std::reverse_iterator<iterator>;using const_reverse_iterator = std::reverse_iterator<const_iterator>;constexpr list() : list(Allocator()) { } constexpr explicit list(const Allocator&);constexpr explicit list(size_type n, const Allocator& = Allocator());constexpr list(size_type n, const T& value, const Allocator& = Allocator());template<class InputIterator> constexpr list(InputIterator first, InputIterator last, const Allocator& = Allocator());template<container-compatible-range<T> R> constexpr list(from_range_t, R&& rg, const Allocator& = Allocator());constexpr list(const list& x);constexpr list(list&& x);constexpr list(const list&, const type_identity_t<Allocator>&);constexpr list(list&&, const type_identity_t<Allocator>&);constexpr list(initializer_list<T>, const Allocator& = Allocator());constexpr ~list();constexpr list& operator=(const list& x);constexpr list& operator=(list&& x) noexcept(allocator_traits<Allocator>::is_always_equal::value);constexpr list& operator=(initializer_list<T>);template<class InputIterator> constexpr void assign(InputIterator first, InputIterator last);template<container-compatible-range<T> R> constexpr void assign_range(R&& rg);constexpr void assign(size_type n, const T& t);constexpr void assign(initializer_list<T>);constexpr allocator_type get_allocator() const noexcept;constexpr iterator begin() noexcept;constexpr const_iterator begin() const noexcept;constexpr iterator end() noexcept;constexpr const_iterator end() const noexcept;constexpr reverse_iterator rbegin() noexcept;constexpr const_reverse_iterator rbegin() const noexcept;constexpr reverse_iterator rend() noexcept;constexpr const_reverse_iterator rend() const noexcept;constexpr const_iterator cbegin() const noexcept;constexpr const_iterator cend() const noexcept;constexpr const_reverse_iterator crbegin() const noexcept;constexpr const_reverse_iterator crend() const noexcept;constexpr bool empty() const noexcept;constexpr size_type size() const noexcept;constexpr size_type max_size() const noexcept;constexpr void resize(size_type sz);constexpr void resize(size_type sz, const T& c);constexpr reference front();constexpr const_reference front() const;constexpr reference back();constexpr const_reference back() const;template<class... Args> constexpr reference emplace_front(Args&&... args);template<class... Args> constexpr reference emplace_back(Args&&... args);constexpr void push_front(const T& x);constexpr void push_front(T&& x);template<container-compatible-range<T> R> constexpr void prepend_range(R&& rg);constexpr void pop_front();constexpr void push_back(const T& x);constexpr void push_back(T&& x);template<container-compatible-range<T> R> constexpr void append_range(R&& rg);constexpr void pop_back();template<class... Args> constexpr iterator emplace(const_iterator position, Args&&... args);constexpr iterator insert(const_iterator position, const T& x);constexpr iterator insert(const_iterator position, T&& x);constexpr iterator insert(const_iterator position, size_type n, const T& x);template<class InputIterator> constexpr iterator insert(const_iterator position, InputIterator first, InputIterator last);template<container-compatible-range<T> R> constexpr iterator insert_range(const_iterator position, R&& rg);constexpr iterator insert(const_iterator position, initializer_list<T> il);constexpr iterator erase(const_iterator position);constexpr iterator erase(const_iterator position, const_iterator last);constexpr void swap(list&) noexcept(allocator_traits<Allocator>::is_always_equal::value);constexpr void clear() noexcept;constexpr void splice(const_iterator position, list& x);constexpr void splice(const_iterator position, list&& x);constexpr void splice(const_iterator position, list& x, const_iterator i);constexpr void splice(const_iterator position, list&& x, const_iterator i);constexpr void splice(const_iterator position, list& x, const_iterator first, const_iterator last);constexpr void splice(const_iterator position, list&& x, const_iterator first, const_iterator last);constexpr size_type remove(const T& value);template<class Predicate> constexpr size_type remove_if(Predicate pred);constexpr size_type unique();template<class BinaryPredicate> constexpr size_type unique(BinaryPredicate binary_pred);constexpr void merge(list& x);constexpr void merge(list&& x);template<class Compare> constexpr void merge(list& x, Compare comp);template<class Compare> constexpr void merge(list&& x, Compare comp);constexpr void sort();template<class Compare> constexpr void sort(Compare comp);constexpr void reverse() noexcept;};template<class InputIterator, class Allocator = allocator<_iter-value-type_<InputIterator>>> list(InputIterator, InputIterator, Allocator = Allocator()) -> list<_iter-value-type_<InputIterator>, Allocator>;template<ranges::input_range R, class Allocator = allocator<ranges::range_value_t<R>>> list(from_range_t, R&&, Allocator = Allocator()) -> list<ranges::range_value_t<R>, Allocator>;}
T shall be complete before any member of the resulting specialization of list is referenced.
23.3.11.2 Constructors, copy, and assignment [list.cons]
constexpr explicit list(const Allocator&);
Effects: Constructs an empty list, using the specified allocator.
constexpr explicit list(size_type n, const Allocator& = Allocator());
Preconditions: T is Cpp17DefaultInsertable into list.
Effects: Constructs a list withn default-inserted elements using the specified allocator.
constexpr list(size_type n, const T& value, const Allocator& = Allocator());
Preconditions: T is Cpp17CopyInsertable into list.
Effects: Constructs alistwithncopies ofvalue, using the specified allocator.
template<class InputIterator> constexpr list(InputIterator first, InputIterator last, const Allocator& = Allocator());
Effects: Constructs alistequal to the range [first, last).
Complexity: Linear indistance(first, last).
Effects: Constructs a list object with the elements of the range rg.
Complexity: Linear in ranges::distance(rg).
23.3.11.3 Capacity [list.capacity]
constexpr void resize(size_type sz);
Preconditions: T is Cpp17DefaultInsertable into list.
Effects: If size() < sz, appends sz - size() default-inserted elements to the sequence.
If sz <= size(), equivalent to:list<T>::iterator it = begin(); advance(it, sz); erase(it, end());
constexpr void resize(size_type sz, const T& c);
Preconditions: T is Cpp17CopyInsertable into list.
Effects: As if by:if (sz > size()) insert(end(), sz-size(), c);else if (sz < size()) { iterator i = begin(); advance(i, sz); erase(i, end());} else ;
23.3.11.4 Modifiers [list.modifiers]
constexpr iterator insert(const_iterator position, const T& x);constexpr iterator insert(const_iterator position, T&& x);constexpr iterator insert(const_iterator position, size_type n, const T& x);template<class InputIterator> constexpr iterator insert(const_iterator position, InputIterator first, InputIterator last);template<[_container-compatible-range_](container.intro.reqmts#concept:container-compatible-range "23.2.2.1 Introduction [container.intro.reqmts]")<T> R> constexpr iterator insert_range(const_iterator position, R&& rg);constexpr iterator insert(const_iterator position, initializer_list<T>);template<class... Args> constexpr reference emplace_front(Args&&... args);template<class... Args> constexpr reference emplace_back(Args&&... args);template<class... Args> constexpr iterator emplace(const_iterator position, Args&&... args);constexpr void push_front(const T& x);constexpr void push_front(T&& x);template<[_container-compatible-range_](container.intro.reqmts#concept:container-compatible-range "23.2.2.1 Introduction [container.intro.reqmts]")<T> R> constexpr void prepend_range(R&& rg);constexpr void push_back(const T& x);constexpr void push_back(T&& x);template<[_container-compatible-range_](container.intro.reqmts#concept:container-compatible-range "23.2.2.1 Introduction [container.intro.reqmts]")<T> R> constexpr void append_range(R&& rg);
Complexity: Insertion of a single element into a list takes constant time and exactly one call to a constructor ofT.
Insertion of multiple elements into a list is linear in the number of elements inserted, and the number of calls to the copy constructor or move constructor of T is exactly equal to the number of elements inserted.
Remarks: Does not affect the validity of iterators and references.
If an exception is thrown, there are no effects.
constexpr iterator erase(const_iterator position);constexpr iterator erase(const_iterator first, const_iterator last);constexpr void pop_front();constexpr void pop_back();constexpr void clear() noexcept;
Effects: Invalidates only the iterators and references to the erased elements.
Complexity: Erasing a single element is a constant time operation with a single call to the destructor ofT.
Erasing a range in a list is linear time in the size of the range and the number of calls to the destructor of typeTis exactly equal to the size of the range.
23.3.11.5 Operations [list.ops]
Since lists allow fast insertion and erasing from the middle of a list, certain operations are provided specifically for them.197
In this subclause, arguments for a template parameter named Predicate or BinaryPredicateshall meet the corresponding requirements in [algorithms.requirements].
The semantics of i + n and i - n, where i is an iterator into the list and n is an integer, are the same as those of next(i, n) and prev(i, n), respectively.
For merge and sort, the definitions and requirements in [alg.sorting] apply.
list provides three splice operations that destructively move elements from one list to another.
The behavior of splice operations is undefined if get_allocator() !=x.get_allocator().
constexpr void splice(const_iterator position, list& x);constexpr void splice(const_iterator position, list&& x);
Preconditions: addressof(x) != this is true.
Effects: Inserts the contents ofxbeforepositionandxbecomes empty.
Pointers and references to the moved elements ofxnow refer to those same elements but as members of*this.
Iterators referring to the moved elements will continue to refer to their elements, but they now behave as iterators into*this, not intox.
Complexity: Constant time.
constexpr void splice(const_iterator position, list& x, const_iterator i);constexpr void splice(const_iterator position, list&& x, const_iterator i);
Preconditions: i is a valid dereferenceable iterator of x.
Effects: Inserts an element pointed to byifrom listxbefore position and removes the element fromx.
The result is unchanged ifposition == iorposition == ++i.
Pointers and references to*icontinue to refer to this same element but as a member of*this.
Iterators to*i(includingiitself) continue to refer to the same element, but now behave as iterators into*this, not intox.
Complexity: Constant time.
constexpr void splice(const_iterator position, list& x, const_iterator first, const_iterator last);constexpr void splice(const_iterator position, list&& x, const_iterator first, const_iterator last);
Preconditions: [first, last) is a valid range in x.
position is not an iterator in the range [first, last).
Effects: Inserts elements in the range [first, last) beforepositionand removes the elements fromx.
Pointers and references to the moved elements ofxnow refer to those same elements but as members of*this.
Iterators referring to the moved elements will continue to refer to their elements, but they now behave as iterators into*this, not intox.
Complexity: Constant time ifaddressof(x) == this; otherwise, linear time.
constexpr size_type remove(const T& value);template<class Predicate> constexpr size_type remove_if(Predicate pred);
Effects: Erases all the elements in the list referred to by a list iterator i for which the following conditions hold: *i == value, pred(*i) != false.
Invalidates only the iterators and references to the erased elements.
Returns: The number of elements erased.
Throws: Nothing unless an exception is thrown by*i == valueorpred(*i) != false.
Complexity: Exactlysize()applications of the corresponding predicate.
constexpr size_type unique();template<class BinaryPredicate> constexpr size_type unique(BinaryPredicate binary_pred);
Let binary_pred be equal_to<>{} for the first overload.
Preconditions: binary_pred is an equivalence relation.
Effects: Erases all but the first element from every consecutive group of equivalent elements.
That is, for a nonempty list, erases all elements referred to by the iterator i in the range [begin() + 1, end()) for which binary_pred(*i, *(i - 1)) is true.
Invalidates only the iterators and references to the erased elements.
Returns: The number of elements erased.
Throws: Nothing unless an exception is thrown by the predicate.
Complexity: If empty() is false, exactly size() - 1 applications of the corresponding predicate, otherwise no applications of the predicate.
constexpr void merge(list& x);constexpr void merge(list&& x);template<class Compare> constexpr void merge(list& x, Compare comp);template<class Compare> constexpr void merge(list&& x, Compare comp);
Let comp be less<> for the first two overloads.
Preconditions: *this and x are both sorted with respect to the comparator comp, andget_allocator() == x.get_allocator() is true.
Effects: If addressof(x) == this, there are no effects.
Otherwise, merges the two sorted ranges [begin(), end()) and [x.begin(), x.end()).
The result is a range that is sorted with respect to the comparator comp.
Pointers and references to the moved elements of x now refer to those same elements but as members of *this.
Iterators referring to the moved elements will continue to refer to their elements, but they now behave as iterators into *this, not intox.
Complexity: At most size() + x.size() - 1 comparisons if addressof(x) != this; otherwise, no comparisons are performed.
If addressof(x) != this, x is empty after the merge.
No elements are copied by this operation.
If an exception is thrown other than by a comparison, there are no effects.
constexpr void reverse() noexcept;
Effects: Reverses the order of the elements in the list.
Does not affect the validity of iterators and references.
void sort();template<class Compare> void sort(Compare comp);
Effects: Sorts the list according to the operator< or a Compare function object.
If an exception is thrown, the order of the elements in *this is unspecified.
Does not affect the validity of iterators and references.
Complexity: Approximatelycomparisons, whereN == size().
23.3.11.6 Erasure [list.erasure]
template<class T, class Allocator, class U = T> typename list<T, Allocator>::size_typeconstexpr erase(list<T, Allocator>& c, const U& value);
Effects: Equivalent to: return erase_if(c, [&](const auto& elem) -> bool { return elem == value; });
template<class T, class Allocator, class Predicate> typename list<T, Allocator>::size_typeconstexpr erase_if(list<T, Allocator>& c, Predicate pred);
Effects: Equivalent to: return c.remove_if(pred);
23.3.13 Class template vector [vector]
23.3.13.1 Overview [vector.overview]
Avectoris a sequence container that supports (amortized) constant time insert and erase operations at the end; insert and erase in the middle take linear time.
Storage management is handled automatically, though hints can be given to improve efficiency.
The exceptions are thepush_front, prepend_range, pop_front, and emplace_front member functions, which are not provided.
Descriptions are provided here only for operations on vectorthat are not described in one of these tables or for operations where there is additional semantic information.
namespace std { template<class T, class Allocator = allocator<T>> class vector { public: using value_type = T;using allocator_type = Allocator;using pointer = typename allocator_traits<Allocator>::pointer;using const_pointer = typename allocator_traits<Allocator>::const_pointer;using reference = value_type&;using const_reference = const value_type&;using size_type = implementation-defined; using difference_type = implementation-defined; using iterator = implementation-defined; using const_iterator = implementation-defined; using reverse_iterator = std::reverse_iterator<iterator>;using const_reverse_iterator = std::reverse_iterator<const_iterator>;constexpr vector() noexcept(noexcept(Allocator())) : vector(Allocator()) { } constexpr explicit vector(const Allocator&) noexcept;constexpr explicit vector(size_type n, const Allocator& = Allocator());constexpr vector(size_type n, const T& value, const Allocator& = Allocator());template<class InputIterator> constexpr vector(InputIterator first, InputIterator last, const Allocator& = Allocator());template<container-compatible-range<T> R> constexpr vector(from_range_t, R&& rg, const Allocator& = Allocator());constexpr vector(const vector& x);constexpr vector(vector&&) noexcept;constexpr vector(const vector&, const type_identity_t<Allocator>&);constexpr vector(vector&&, const type_identity_t<Allocator>&);constexpr vector(initializer_list<T>, const Allocator& = Allocator());constexpr ~vector();constexpr vector& operator=(const vector& x);constexpr vector& operator=(vector&& x) noexcept(allocator_traits<Allocator>::propagate_on_container_move_assignment::value || allocator_traits<Allocator>::is_always_equal::value);constexpr vector& operator=(initializer_list<T>);template<class InputIterator> constexpr void assign(InputIterator first, InputIterator last);template<container-compatible-range<T> R> constexpr void assign_range(R&& rg);constexpr void assign(size_type n, const T& u);constexpr void assign(initializer_list<T>);constexpr allocator_type get_allocator() const noexcept;constexpr iterator begin() noexcept;constexpr const_iterator begin() const noexcept;constexpr iterator end() noexcept;constexpr const_iterator end() const noexcept;constexpr reverse_iterator rbegin() noexcept;constexpr const_reverse_iterator rbegin() const noexcept;constexpr reverse_iterator rend() noexcept;constexpr const_reverse_iterator rend() const noexcept;constexpr const_iterator cbegin() const noexcept;constexpr const_iterator cend() const noexcept;constexpr const_reverse_iterator crbegin() const noexcept;constexpr const_reverse_iterator crend() const noexcept;constexpr bool empty() const noexcept;constexpr size_type size() const noexcept;constexpr size_type max_size() const noexcept;constexpr size_type capacity() const noexcept;constexpr void resize(size_type sz);constexpr void resize(size_type sz, const T& c);constexpr void reserve(size_type n);constexpr void shrink_to_fit();constexpr reference operator[](size_type n);constexpr const_reference operator[](size_type n) const;constexpr reference at(size_type n);constexpr const_reference at(size_type n) const;constexpr reference front();constexpr const_reference front() const;constexpr reference back();constexpr const_reference back() const;constexpr T* data() noexcept;constexpr const T* data() const noexcept;template<class... Args> constexpr reference emplace_back(Args&&... args);constexpr void push_back(const T& x);constexpr void push_back(T&& x);template<container-compatible-range<T> R> constexpr void append_range(R&& rg);constexpr void pop_back();template<class... Args> constexpr iterator emplace(const_iterator position, Args&&... args);constexpr iterator insert(const_iterator position, const T& x);constexpr iterator insert(const_iterator position, T&& x);constexpr iterator insert(const_iterator position, size_type n, const T& x);template<class InputIterator> constexpr iterator insert(const_iterator position, InputIterator first, InputIterator last);template<container-compatible-range<T> R> constexpr iterator insert_range(const_iterator position, R&& rg);constexpr iterator insert(const_iterator position, initializer_list<T> il);constexpr iterator erase(const_iterator position);constexpr iterator erase(const_iterator first, const_iterator last);constexpr void swap(vector&) noexcept(allocator_traits<Allocator>::propagate_on_container_swap::value || allocator_traits<Allocator>::is_always_equal::value);constexpr void clear() noexcept;};template<class InputIterator, class Allocator = allocator<_iter-value-type_<InputIterator>>> vector(InputIterator, InputIterator, Allocator = Allocator()) -> vector<_iter-value-type_<InputIterator>, Allocator>;template<ranges::input_range R, class Allocator = allocator<ranges::range_value_t<R>>> vector(from_range_t, R&&, Allocator = Allocator()) -> vector<ranges::range_value_t<R>, Allocator>;}
T shall be complete before any member of the resulting specialization of vector is referenced.
23.3.13.2 Constructors [vector.cons]
constexpr explicit vector(const Allocator&) noexcept;
Effects: Constructs an empty vector, using the specified allocator.
constexpr explicit vector(size_type n, const Allocator& = Allocator());
Preconditions: T is Cpp17DefaultInsertable into vector.
Effects: Constructs a vector with ndefault-inserted elements using the specified allocator.
constexpr vector(size_type n, const T& value,const Allocator& = Allocator());
Preconditions: T is_Cpp17CopyInsertable_ into vector.
Effects: Constructs a vector with ncopies of value, using the specified allocator.
template<class InputIterator> constexpr vector(InputIterator first, InputIterator last,const Allocator& = Allocator());
Effects: Constructs a vector equal to the range [first, last), using the specified allocator.
Complexity: Makes only Ncalls to the copy constructor ofT(where Nis the distance betweenfirstandlast) and no reallocations if iterators first and last are of forward, bidirectional, or random access categories.
It makes orderNcalls to the copy constructor ofTand orderreallocations if they are just input iterators.
Effects: Constructs a vector object with the elements of the range rg, using the specified allocator.
Complexity: Initializes exactly N elements from the results of dereferencing successive iterators of rg, where N is ranges::distance(rg).
Performs no reallocations if:
- R models ranges::approximately_sized_range, andranges::distance(rg) <= ranges::reserve_hint(rg) is true, or
- R models ranges::forward_range andR does not model ranges::approximately_sized_range.
Otherwise, performs order reallocations and order N calls to the copy or move constructor of T.
23.3.13.3 Capacity [vector.capacity]
constexpr size_type capacity() const noexcept;
Returns: The total number of elements that the vector can hold without requiring reallocation.
Complexity: Constant time.
constexpr void reserve(size_type n);
Preconditions: T is Cpp17MoveInsertable into vector.
Effects: A directive that informs avectorof a planned change in size, so that it can manage the storage allocation accordingly.
Afterreserve(),capacity()is greater or equal to the argument ofreserveif reallocation happens; and equal to the previous value ofcapacity()otherwise.
Reallocation happens at this point if and only if the current capacity is less than the argument ofreserve().
If an exception is thrown other than by the move constructor of a non-Cpp17CopyInsertable type, there are no effects.
Throws: length_error if n >max_size().198
Complexity: It does not change the size of the sequence and takes at most linear time in the size of the sequence.
Remarks: Reallocation invalidates all the references, pointers, and iterators referring to the elements in the sequence, as well as the past-the-end iterator.
[Note 1:
If no reallocation happens, they remain valid.
— _end note_]
No reallocation shall take place during insertions that happen after a call to reserve()until an insertion would make the size of the vector greater than the value of capacity().
constexpr void shrink_to_fit();
Preconditions: T is Cpp17MoveInsertable into vector.
Effects: shrink_to_fit is a non-binding request to reducecapacity() to size().
[Note 2:
The request is non-binding to allow latitude for implementation-specific optimizations.
— _end note_]
It does not increase capacity(), but may reduce capacity()by causing reallocation.
If an exception is thrown other than by the move constructor of a non-Cpp17CopyInsertable T, there are no effects.
Complexity: If reallocation happens, linear in the size of the sequence.
Remarks: Reallocation invalidates all the references, pointers, and iterators referring to the elements in the sequence as well as the past-the-end iterator.
[Note 3:
If no reallocation happens, they remain valid.
— _end note_]
constexpr void swap(vector& x) noexcept(allocator_traits<Allocator>::propagate_on_container_swap::value || allocator_traits<Allocator>::is_always_equal::value);
Effects: Exchanges the contents andcapacity()of*thiswith that of x.
Complexity: Constant time.
constexpr void resize(size_type sz);
Preconditions: T is_Cpp17MoveInsertable_ and Cpp17DefaultInsertable into vector.
Effects: If sz < size(), erases the last size() - sz elements from the sequence.
Otherwise, appends sz - size() default-inserted elements to the sequence.
Remarks: If an exception is thrown other than by the move constructor of a non-Cpp17CopyInsertable T, there are no effects.
constexpr void resize(size_type sz, const T& c);
Preconditions: T is_Cpp17CopyInsertable_ into vector.
Effects: If sz < size(), erases the last size() - sz elements from the sequence.
Otherwise, appends sz - size() copies of c to the sequence.
Remarks: If an exception is thrown, there are no effects.
23.3.13.4 Data [vector.data]
constexpr T* data() noexcept;constexpr const T* data() const noexcept;
Returns: A pointer such that [data(), data() + size()) is a valid range.
For a non-empty vector, data() == addressof(front()) is true.
Complexity: Constant time.
23.3.13.5 Modifiers [vector.modifiers]
constexpr iterator insert(const_iterator position, const T& x);constexpr iterator insert(const_iterator position, T&& x);constexpr iterator insert(const_iterator position, size_type n, const T& x);template<class InputIterator> constexpr iterator insert(const_iterator position, InputIterator first, InputIterator last);template<[_container-compatible-range_](container.intro.reqmts#concept:container-compatible-range "23.2.2.1 Introduction [container.intro.reqmts]")<T> R> constexpr iterator insert_range(const_iterator position, R&& rg);constexpr iterator insert(const_iterator position, initializer_list<T>);template<class... Args> constexpr reference emplace_back(Args&&... args);template<class... Args> constexpr iterator emplace(const_iterator position, Args&&... args);constexpr void push_back(const T& x);constexpr void push_back(T&& x);template<[_container-compatible-range_](container.intro.reqmts#concept:container-compatible-range "23.2.2.1 Introduction [container.intro.reqmts]")<T> R> constexpr void append_range(R&& rg);
Complexity: If reallocation happens, linear in the number of elements of the resulting vector; otherwise, linear in the number of elements inserted plus the distance to the end of the vector.
Remarks: Causes reallocation if the new size is greater than the old capacity.
Reallocation invalidates all the references, pointers, and iterators referring to the elements in the sequence, as well as the past-the-end iterator.
If no reallocation happens, then references, pointers, and iterators before the insertion point remain valid but those at or after the insertion point, including the past-the-end iterator, are invalidated.
If an exception is thrown other than by the copy constructor, move constructor, assignment operator, or move assignment operator ofT or by any InputIterator operation, there are no effects.
If an exception is thrown while inserting a single element at the end andT is Cpp17CopyInsertable or is_nothrow_move_constructible_v<T>is true, there are no effects.
Otherwise, if an exception is thrown by the move constructor of a non-Cpp17CopyInsertable T, the effects are unspecified.
For the declarations taking a pair of InputIterator, performs at most one reallocation ifInputIterator models Cpp17ForwardIterator.
constexpr iterator erase(const_iterator position);constexpr iterator erase(const_iterator first, const_iterator last);constexpr void pop_back();
Effects: Invalidates iterators and references at or after the point of the erase.
Throws: Nothing unless an exception is thrown by the assignment operator or move assignment operator ofT.
Complexity: The destructor of T is called the number of times equal to the number of the elements erased, but the assignment operator of T is called the number of times equal to the number of elements in the vector after the erased elements.
23.3.13.6 Erasure [vector.erasure]
template<class T, class Allocator, class U = T> constexpr typename vector<T, Allocator>::size_type erase(vector<T, Allocator>& c, const U& value);
Effects: Equivalent to:auto it = remove(c.begin(), c.end(), value);auto r = distance(it, c.end()); c.erase(it, c.end());return r;
template<class T, class Allocator, class Predicate> constexpr typename vector<T, Allocator>::size_type erase_if(vector<T, Allocator>& c, Predicate pred);
Effects: Equivalent to:auto it = remove_if(c.begin(), c.end(), pred);auto r = distance(it, c.end()); c.erase(it, c.end());return r;
23.3.14 Specialization of vector for bool [vector.bool]
23.3.14.1 Partial class template specialization vector<bool, Allocator> [vector.bool.pspc]
To optimize space allocation, a partial specialization of vector forbool elements is provided:namespace std { template<class Allocator> class vector<bool, Allocator> { public: using value_type = bool;using allocator_type = Allocator;using pointer = implementation-defined;using const_pointer = implementation-defined;using const_reference = bool;using size_type = implementation-defined; using difference_type = implementation-defined; using iterator = implementation-defined; using const_iterator = implementation-defined; using reverse_iterator = std::reverse_iterator<iterator>;using const_reverse_iterator = std::reverse_iterator<const_iterator>;class reference { public: constexpr reference(const reference&) = default;constexpr ~reference();constexpr operator bool() const noexcept;constexpr reference& operator=(bool x) noexcept;constexpr reference& operator=(const reference& x) noexcept;constexpr const reference& operator=(bool x) const noexcept;constexpr void flip() noexcept; };constexpr vector() noexcept(noexcept(Allocator())) : vector(Allocator()) { } constexpr explicit vector(const Allocator&) noexcept;constexpr explicit vector(size_type n, const Allocator& = Allocator());constexpr vector(size_type n, const bool& value, const Allocator& = Allocator());template<class InputIterator> constexpr vector(InputIterator first, InputIterator last, const Allocator& = Allocator());template<container-compatible-range<bool> R> constexpr vector(from_range_t, R&& rg, const Allocator& = Allocator());constexpr vector(const vector& x);constexpr vector(vector&& x) noexcept;constexpr vector(const vector&, const type_identity_t<Allocator>&);constexpr vector(vector&&, const type_identity_t<Allocator>&);constexpr vector(initializer_list<bool>, const Allocator& = Allocator());constexpr ~vector();constexpr vector& operator=(const vector& x);constexpr vector& operator=(vector&& x) noexcept(allocator_traits<Allocator>::propagate_on_container_move_assignment::value || allocator_traits<Allocator>::is_always_equal::value);constexpr vector& operator=(initializer_list<bool>);template<class InputIterator> constexpr void assign(InputIterator first, InputIterator last);template<container-compatible-range<bool> R> constexpr void assign_range(R&& rg);constexpr void assign(size_type n, const bool& t);constexpr void assign(initializer_list<bool>);constexpr allocator_type get_allocator() const noexcept;constexpr iterator begin() noexcept;constexpr const_iterator begin() const noexcept;constexpr iterator end() noexcept;constexpr const_iterator end() const noexcept;constexpr reverse_iterator rbegin() noexcept;constexpr const_reverse_iterator rbegin() const noexcept;constexpr reverse_iterator rend() noexcept;constexpr const_reverse_iterator rend() const noexcept;constexpr const_iterator cbegin() const noexcept;constexpr const_iterator cend() const noexcept;constexpr const_reverse_iterator crbegin() const noexcept;constexpr const_reverse_iterator crend() const noexcept;constexpr bool empty() const noexcept;constexpr size_type size() const noexcept;constexpr size_type max_size() const noexcept;constexpr size_type capacity() const noexcept;constexpr void resize(size_type sz, bool c = false);constexpr void reserve(size_type n);constexpr void shrink_to_fit();constexpr reference operator[](size_type n);constexpr const_reference operator[](size_type n) const;constexpr reference at(size_type n);constexpr const_reference at(size_type n) const;constexpr reference front();constexpr const_reference front() const;constexpr reference back();constexpr const_reference back() const;template<class... Args> constexpr reference emplace_back(Args&&... args);constexpr void push_back(const bool& x);template<container-compatible-range<bool> R> constexpr void append_range(R&& rg);constexpr void pop_back();template<class... Args> constexpr iterator emplace(const_iterator position, Args&&... args);constexpr iterator insert(const_iterator position, const bool& x);constexpr iterator insert(const_iterator position, size_type n, const bool& x);template<class InputIterator> constexpr iterator insert(const_iterator position, InputIterator first, InputIterator last);template<container-compatible-range<bool> R> constexpr iterator insert_range(const_iterator position, R&& rg);constexpr iterator insert(const_iterator position, initializer_list<bool> il);constexpr iterator erase(const_iterator position);constexpr iterator erase(const_iterator first, const_iterator last);constexpr void swap(vector&) noexcept(allocator_traits<Allocator>::propagate_on_container_swap::value || allocator_traits<Allocator>::is_always_equal::value);static constexpr void swap(reference x, reference y) noexcept;constexpr void flip() noexcept; constexpr void clear() noexcept;};}
Unless described below, all operations have the same requirements and semantics as the primary vector template, except that operations dealing with the bool value type map to bit values in the container storage andallocator_traits::constructis not used to construct these values.
There is no requirement that the data be stored as a contiguous allocation of bool values.
A space-optimized representation of bits is recommended instead.
referenceis a class that simulates the behavior of references of a single bit invector<bool>.
The conversion function returns truewhen the bit is set, and false otherwise.
The assignment operators set the bit when the argument is (convertible to) true and clear it otherwise.
flip reverses the state of the bit.
constexpr void flip() noexcept;
Effects: Replaces each element in the container with its complement.
static constexpr void swap(reference x, reference y) noexcept;
Effects: Exchanges the contents of x and y as if by:bool b = x; x = y; y = b;
template<class Allocator> struct hash<vector<bool, Allocator>>;
template<class T> constexpr bool _is-vector-bool-reference_ = _see below_;
The expression_is-vector-bool-reference_<T> is trueif T denotes the type vector<bool, Alloc>::referencefor some type Alloc andvector<bool, Alloc> is not a program-defined specialization.
23.3.14.2 Formatter specialization for vector [vector.bool.fmt]
namespace std { template<class T, class charT> requires is-vector-bool-reference<T> struct formatter<T, charT> { private: formatter<bool, charT> underlying_; public: template<class ParseContext> constexpr typename ParseContext::iterator parse(ParseContext& ctx);template<class FormatContext> typename FormatContext::iterator format(const T& ref, FormatContext& ctx) const;};}
template<class ParseContext> constexpr typename ParseContext::iterator parse(ParseContext& ctx);
Equivalent to: return underlying_.parse(ctx);
template<class FormatContext> typename FormatContext::iterator format(const T& ref, FormatContext& ctx) const;
Equivalent to: return underlying_.format(ref, ctx);
23.3.16 Class template inplace_vector [inplace.vector]
23.3.16.1 Overview [inplace.vector.overview]
An inplace_vector is a contiguous container.
Its capacity is fixed and its elements are stored within the inplace_vector object itself.
An inplace_vector meets all of the requirements of a container ([container.reqmts]), of a reversible container ([container.rev.reqmts]), of a contiguous container, and of a sequence container, including most of the optional sequence container requirements ([sequence.reqmts]).
The exceptions are thepush_front,prepend_range,pop_front, andemplace_frontmember functions, which are not provided.
Descriptions are provided here only for operations on inplace_vector that are not described in one of these tables or for operations where there is additional semantic information.
For any N,inplace_vector<T, N>::iterator andinplace_vector<T, N>::const_iteratormeet the constexpr iterator requirements.
Any member function of inplace_vector<T, N> that would cause the size to exceed Nthrows an exception of type bad_alloc.
Let IV denote a specialization of inplace_vector<T, N>.
If N is zero, thenIV is trivially copyable and empty, andstd::is_trivially_default_constructible_v<IV> is true.
Otherwise:
- If is_trivially_copy_constructible_v<T> is true, thenIV has a trivial copy constructor.
- If is_trivially_move_constructible_v<T> is true, thenIV has a trivial move constructor.
- If is_trivially_destructible_v<T> is true, then:
- IV has a trivial destructor.
- If is_trivially_copy_constructible_v<T> && is_trivially_copy_assignable_v<T> is true, thenIV has a trivial copy assignment operator.
- If is_trivially_move_constructible_v<T> && is_trivially_move_assignable_v<T> is true, thenIV has a trivial move assignment operator.
namespace std { template<class T, size_t N> class inplace_vector { public: using value_type = T;using pointer = T*;using const_pointer = const T*;using reference = value_type&;using const_reference = const value_type&;using size_type = size_t;using difference_type = ptrdiff_t;using iterator = implementation-defined; using const_iterator = implementation-defined; using reverse_iterator = std::reverse_iterator<iterator>;using const_reverse_iterator = std::reverse_iterator<const_iterator>;constexpr inplace_vector() noexcept;constexpr explicit inplace_vector(size_type n); constexpr inplace_vector(size_type n, const T& value); template<class InputIterator> constexpr inplace_vector(InputIterator first, InputIterator last); template<container-compatible-range<T> R> constexpr inplace_vector(from_range_t, R&& rg); constexpr inplace_vector(const inplace_vector&);constexpr inplace_vector(inplace_vector&&) noexcept(N == 0 || is_nothrow_move_constructible_v<T>);constexpr inplace_vector(initializer_list<T> il); constexpr ~inplace_vector();constexpr inplace_vector& operator=(const inplace_vector& other);constexpr inplace_vector& operator=(inplace_vector&& other) noexcept(N == 0 || (is_nothrow_move_assignable_v<T> && is_nothrow_move_constructible_v<T>));constexpr inplace_vector& operator=(initializer_list<T>); template<class InputIterator> constexpr void assign(InputIterator first, InputIterator last); template<container-compatible-range<T> R> constexpr void assign_range(R&& rg); constexpr void assign(size_type n, const T& u); constexpr void assign(initializer_list<T> il); constexpr iterator begin() noexcept;constexpr const_iterator begin() const noexcept;constexpr iterator end() noexcept;constexpr const_iterator end() const noexcept;constexpr reverse_iterator rbegin() noexcept;constexpr const_reverse_iterator rbegin() const noexcept;constexpr reverse_iterator rend() noexcept;constexpr const_reverse_iterator rend() const noexcept;constexpr const_iterator cbegin() const noexcept;constexpr const_iterator cend() const noexcept;constexpr const_reverse_iterator crbegin() const noexcept;constexpr const_reverse_iterator crend() const noexcept;constexpr bool empty() const noexcept;constexpr size_type size() const noexcept;static constexpr size_type max_size() noexcept;static constexpr size_type capacity() noexcept;constexpr void resize(size_type sz); constexpr void resize(size_type sz, const T& c); static constexpr void reserve(size_type n); static constexpr void shrink_to_fit() noexcept;constexpr reference operator[](size_type n);constexpr const_reference operator[](size_type n) const;constexpr reference at(size_type n); constexpr const_reference at(size_type n) const; constexpr reference front();constexpr const_reference front() const;constexpr reference back();constexpr const_reference back() const;constexpr T* data() noexcept;constexpr const T* data() const noexcept;template<class... Args> constexpr reference emplace_back(Args&&... args); constexpr reference push_back(const T& x); constexpr reference push_back(T&& x); template<container-compatible-range<T> R> constexpr void append_range(R&& rg); constexpr void pop_back();template<class... Args> constexpr pointer try_emplace_back(Args&&... args);constexpr pointer try_push_back(const T& x);constexpr pointer try_push_back(T&& x);template<container-compatible-range<T> R> constexpr ranges::borrowed_iterator_t<R> try_append_range(R&& rg);template<class... Args> constexpr reference unchecked_emplace_back(Args&&... args);constexpr reference unchecked_push_back(const T& x);constexpr reference unchecked_push_back(T&& x);template<class... Args> constexpr iterator emplace(const_iterator position, Args&&... args); constexpr iterator insert(const_iterator position, const T& x); constexpr iterator insert(const_iterator position, T&& x); constexpr iterator insert(const_iterator position, size_type n, const T& x);template<class InputIterator> constexpr iterator insert(const_iterator position, InputIterator first, InputIterator last);template<container-compatible-range<T> R> constexpr iterator insert_range(const_iterator position, R&& rg); constexpr iterator insert(const_iterator position, initializer_list<T> il);constexpr iterator erase(const_iterator position);constexpr iterator erase(const_iterator first, const_iterator last);constexpr void swap(inplace_vector& x) noexcept(N == 0 || (is_nothrow_swappable_v<T> && is_nothrow_move_constructible_v<T>));constexpr void clear() noexcept;constexpr friend bool operator==(const inplace_vector& x,const inplace_vector& y);constexpr friend synth-three-way-result<T> operator<=>(const inplace_vector& x, const inplace_vector& y);constexpr friend void swap(inplace_vector& x, inplace_vector& y) noexcept(N == 0 || (is_nothrow_swappable_v<T> && is_nothrow_move_constructible_v<T>)) { x.swap(y); } };}
23.3.16.2 Constructors [inplace.vector.cons]
constexpr explicit inplace_vector(size_type n);
Preconditions: T is Cpp17DefaultInsertable into inplace_vector.
Effects: Constructs an inplace_vector with n default-inserted elements.
constexpr inplace_vector(size_type n, const T& value);
Preconditions: T is Cpp17CopyInsertable into inplace_vector.
Effects: Constructs an inplace_vector with n copies of value.
template<class InputIterator> constexpr inplace_vector(InputIterator first, InputIterator last);
Effects: Constructs an inplace_vector equal to the range [first, last).
Complexity: Linear in distance(first, last).
Effects: Constructs an inplace_vector with the elements of the range rg.
Complexity: Linear in ranges::distance(rg).
23.3.16.3 Size and capacity [inplace.vector.capacity]
static constexpr size_type capacity() noexcept;static constexpr size_type max_size() noexcept;
constexpr void resize(size_type sz);
Preconditions: T is Cpp17DefaultInsertable into inplace_vector.
Effects: If sz < size(), erases the last size() - sz elements from the sequence.
Otherwise, appends sz - size() default-inserted elements to the sequence.
Remarks: If an exception is thrown, there are no effects on *this.
constexpr void resize(size_type sz, const T& c);
Preconditions: T is Cpp17CopyInsertable into inplace_vector.
Effects: If sz < size(), erases the last size() - sz elements from the sequence.
Otherwise, appends sz - size() copies of c to the sequence.
Remarks: If an exception is thrown, there are no effects on *this.
23.3.16.4 Data [inplace.vector.data]
constexpr T* data() noexcept;constexpr const T* data() const noexcept;
Returns: A pointer such that [data(), data() + size()) is a valid range.
For a non-empty inplace_vector,data() == addressof(front()) is true.
Complexity: Constant time.
23.3.16.5 Modifiers [inplace.vector.modifiers]
constexpr iterator insert(const_iterator position, const T& x);constexpr iterator insert(const_iterator position, T&& x);constexpr iterator insert(const_iterator position, size_type n, const T& x);template<class InputIterator> constexpr iterator insert(const_iterator position, InputIterator first, InputIterator last);template<[_container-compatible-range_](container.intro.reqmts#concept:container-compatible-range "23.2.2.1 Introduction [container.intro.reqmts]")<T> R> constexpr iterator insert_range(const_iterator position, R&& rg);constexpr iterator insert(const_iterator position, initializer_list<T> il);template<class... Args> constexpr iterator emplace(const_iterator position, Args&&... args);template<[_container-compatible-range_](container.intro.reqmts#concept:container-compatible-range "23.2.2.1 Introduction [container.intro.reqmts]")<T> R> constexpr void append_range(R&& rg);
Let n be the value of size() before this call for the append_range overload, anddistance(begin, position) otherwise.
Complexity: Linear in the number of elements inserted plus the distance to the end of the vector.
Remarks: If an exception is thrown other than by the copy constructor, move constructor, assignment operator, or move assignment operator of T or by any InputIterator operation, there are no effects.
Otherwise, if an exception is thrown, thensize() ≥ n and elements in the range begin() + [0, n) are not modified.
constexpr reference push_back(const T& x);constexpr reference push_back(T&& x);template<class... Args> constexpr reference emplace_back(Args&&... args);
Throws: bad_alloc or any exception thrown by the initialization of the inserted element.
Remarks: If an exception is thrown, there are no effects on *this.
template<class... Args> constexpr pointer try_emplace_back(Args&&... args);constexpr pointer try_push_back(const T& x);constexpr pointer try_push_back(T&& x);
Let vals denote a pack:
- std::forward<Args>(args)... for the first overload,
- x for the second overload,
- std::move(x) for the third overload.
Preconditions: value_type is _Cpp17EmplaceConstructible_into inplace_vector from vals....
Effects: If size() < capacity() is true, appends an object of type Tdirect-non-list-initialized with vals....
Otherwise, there are no effects.
Returns: nullptr if size() == capacity() is true, otherwise addressof(back()).
Throws: Nothing unless an exception is thrown by the initialization of the inserted element.
Remarks: If an exception is thrown, there are no effects on *this.
Preconditions: value_type is _Cpp17EmplaceConstructible_into inplace_vector from
*ranges::begin(rg).
Effects: Appends copies of initial elements in rg before end(), until all elements are inserted or size() == capacity() is true.
Each iterator in the range rg is dereferenced at most once.
Returns: An iterator pointing to the first element of rgthat was not inserted into *this, or ranges::end(rg) if no such element exists.
Complexity: Linear in the number of elements inserted.
Remarks: Let n be the value of size() prior to this call.
If an exception is thrown after the insertion of k elements, thensize() equals , elements in the range begin() + [0, n) are not modified, and elements in the range begin() + [n, ) correspond to the inserted elements.
template<class... Args> constexpr reference unchecked_emplace_back(Args&&... args);
Preconditions: size() < capacity() is true.
Effects: Equivalent to:return *try_emplace_back(std::forward<Args>(args)...);
constexpr reference unchecked_push_back(const T& x);constexpr reference unchecked_push_back(T&& x);
Preconditions: size() < capacity() is true.
Effects: Equivalent to:return *try_push_back(std::forward<decltype(x)>(x));
static constexpr void reserve(size_type n);
Throws: bad_alloc if n > capacity() is true.
static constexpr void shrink_to_fit() noexcept;
constexpr iterator erase(const_iterator position);constexpr iterator erase(const_iterator first, const_iterator last);constexpr void pop_back();
Effects: Invalidates iterators and references at or after the point of the erase.
Throws: Nothing unless an exception is thrown by the assignment operator or move assignment operator of T.
Complexity: The destructor of T is called the number of times equal to the number of the elements erased, but the assignment operator of T is called the number of times equal to the number of elements after the erased elements.
23.3.16.6 Erasure [inplace.vector.erasure]
template<class T, size_t N, class U = T> constexpr size_t erase(inplace_vector<T, N>& c, const U& value);
Effects: Equivalent to:auto it = remove(c.begin(), c.end(), value);auto r = distance(it, c.end()); c.erase(it, c.end());return r;
template<class T, size_t N, class Predicate> constexpr size_t erase_if(inplace_vector<T, N>& c, Predicate pred);
Effects: Equivalent to:auto it = remove_if(c.begin(), c.end(), pred);auto r = distance(it, c.end()); c.erase(it, c.end());return r;