10b57cec5SDimitry Andric// -*- C++ -*- 2349cc55cSDimitry Andric//===----------------------------------------------------------------------===// 30b57cec5SDimitry Andric// 40b57cec5SDimitry Andric// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 50b57cec5SDimitry Andric// See https://llvm.org/LICENSE.txt for license information. 60b57cec5SDimitry Andric// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 70b57cec5SDimitry Andric// 80b57cec5SDimitry Andric//===----------------------------------------------------------------------===// 90b57cec5SDimitry Andric 100b57cec5SDimitry Andric#ifndef _LIBCPP_ARRAY 110b57cec5SDimitry Andric#define _LIBCPP_ARRAY 120b57cec5SDimitry Andric 130b57cec5SDimitry Andric/* 140b57cec5SDimitry Andric array synopsis 150b57cec5SDimitry Andric 160b57cec5SDimitry Andricnamespace std 170b57cec5SDimitry Andric{ 180b57cec5SDimitry Andrictemplate <class T, size_t N > 190b57cec5SDimitry Andricstruct array 200b57cec5SDimitry Andric{ 210b57cec5SDimitry Andric // types: 220b57cec5SDimitry Andric typedef T & reference; 230b57cec5SDimitry Andric typedef const T & const_reference; 240b57cec5SDimitry Andric typedef implementation defined iterator; 250b57cec5SDimitry Andric typedef implementation defined const_iterator; 260b57cec5SDimitry Andric typedef size_t size_type; 270b57cec5SDimitry Andric typedef ptrdiff_t difference_type; 280b57cec5SDimitry Andric typedef T value_type; 290b57cec5SDimitry Andric typedef T* pointer; 300b57cec5SDimitry Andric typedef const T* const_pointer; 310b57cec5SDimitry Andric typedef std::reverse_iterator<iterator> reverse_iterator; 320b57cec5SDimitry Andric typedef std::reverse_iterator<const_iterator> const_reverse_iterator; 330b57cec5SDimitry Andric 340b57cec5SDimitry Andric // No explicit construct/copy/destroy for aggregate type 355ffd83dbSDimitry Andric void fill(const T& u); // constexpr in C++20 365ffd83dbSDimitry Andric void swap(array& a) noexcept(is_nothrow_swappable_v<T>); // constexpr in C++20 370b57cec5SDimitry Andric 380b57cec5SDimitry Andric // iterators: 395ffd83dbSDimitry Andric iterator begin() noexcept; // constexpr in C++17 405ffd83dbSDimitry Andric const_iterator begin() const noexcept; // constexpr in C++17 415ffd83dbSDimitry Andric iterator end() noexcept; // constexpr in C++17 425ffd83dbSDimitry Andric const_iterator end() const noexcept; // constexpr in C++17 430b57cec5SDimitry Andric 445ffd83dbSDimitry Andric reverse_iterator rbegin() noexcept; // constexpr in C++17 455ffd83dbSDimitry Andric const_reverse_iterator rbegin() const noexcept; // constexpr in C++17 465ffd83dbSDimitry Andric reverse_iterator rend() noexcept; // constexpr in C++17 475ffd83dbSDimitry Andric const_reverse_iterator rend() const noexcept; // constexpr in C++17 480b57cec5SDimitry Andric 495ffd83dbSDimitry Andric const_iterator cbegin() const noexcept; // constexpr in C++17 505ffd83dbSDimitry Andric const_iterator cend() const noexcept; // constexpr in C++17 515ffd83dbSDimitry Andric const_reverse_iterator crbegin() const noexcept; // constexpr in C++17 525ffd83dbSDimitry Andric const_reverse_iterator crend() const noexcept; // constexpr in C++17 530b57cec5SDimitry Andric 540b57cec5SDimitry Andric // capacity: 550b57cec5SDimitry Andric constexpr size_type size() const noexcept; 560b57cec5SDimitry Andric constexpr size_type max_size() const noexcept; 570b57cec5SDimitry Andric constexpr bool empty() const noexcept; 580b57cec5SDimitry Andric 590b57cec5SDimitry Andric // element access: 605ffd83dbSDimitry Andric reference operator[](size_type n); // constexpr in C++17 610b57cec5SDimitry Andric const_reference operator[](size_type n) const; // constexpr in C++14 625ffd83dbSDimitry Andric reference at(size_type n); // constexpr in C++17 630b57cec5SDimitry Andric const_reference at(size_type n) const; // constexpr in C++14 640b57cec5SDimitry Andric 655ffd83dbSDimitry Andric reference front(); // constexpr in C++17 660b57cec5SDimitry Andric const_reference front() const; // constexpr in C++14 675ffd83dbSDimitry Andric reference back(); // constexpr in C++17 680b57cec5SDimitry Andric const_reference back() const; // constexpr in C++14 690b57cec5SDimitry Andric 705ffd83dbSDimitry Andric T* data() noexcept; // constexpr in C++17 715ffd83dbSDimitry Andric const T* data() const noexcept; // constexpr in C++17 720b57cec5SDimitry Andric}; 730b57cec5SDimitry Andric 740b57cec5SDimitry Andrictemplate <class T, class... U> 755ffd83dbSDimitry Andric array(T, U...) -> array<T, 1 + sizeof...(U)>; // C++17 760b57cec5SDimitry Andric 770b57cec5SDimitry Andrictemplate <class T, size_t N> 785ffd83dbSDimitry Andric bool operator==(const array<T,N>& x, const array<T,N>& y); // constexpr in C++20 790b57cec5SDimitry Andrictemplate <class T, size_t N> 8006c3fb27SDimitry Andric bool operator!=(const array<T,N>& x, const array<T,N>& y); // removed in C++20 810b57cec5SDimitry Andrictemplate <class T, size_t N> 8206c3fb27SDimitry Andric bool operator<(const array<T,N>& x, const array<T,N>& y); // removed in C++20 830b57cec5SDimitry Andrictemplate <class T, size_t N> 8406c3fb27SDimitry Andric bool operator>(const array<T,N>& x, const array<T,N>& y); // removed in C++20 850b57cec5SDimitry Andrictemplate <class T, size_t N> 8606c3fb27SDimitry Andric bool operator<=(const array<T,N>& x, const array<T,N>& y); // removed in C++20 870b57cec5SDimitry Andrictemplate <class T, size_t N> 8806c3fb27SDimitry Andric bool operator>=(const array<T,N>& x, const array<T,N>& y); // removed in C++20 8906c3fb27SDimitry Andrictemplate<class T, size_t N> 9006c3fb27SDimitry Andric constexpr synth-three-way-result<T> 9106c3fb27SDimitry Andric operator<=>(const array<T, N>& x, const array<T, N>& y); // since C++20 920b57cec5SDimitry Andric 930b57cec5SDimitry Andrictemplate <class T, size_t N > 945ffd83dbSDimitry Andric void swap(array<T,N>& x, array<T,N>& y) noexcept(noexcept(x.swap(y))); // constexpr in C++20 955ffd83dbSDimitry Andric 965ffd83dbSDimitry Andrictemplate <class T, size_t N> 975ffd83dbSDimitry Andric constexpr array<remove_cv_t<T>, N> to_array(T (&a)[N]); // C++20 985ffd83dbSDimitry Andrictemplate <class T, size_t N> 995ffd83dbSDimitry Andric constexpr array<remove_cv_t<T>, N> to_array(T (&&a)[N]); // C++20 1000b57cec5SDimitry Andric 1010b57cec5SDimitry Andrictemplate <class T> struct tuple_size; 1020b57cec5SDimitry Andrictemplate <size_t I, class T> struct tuple_element; 1030b57cec5SDimitry Andrictemplate <class T, size_t N> struct tuple_size<array<T, N>>; 1040b57cec5SDimitry Andrictemplate <size_t I, class T, size_t N> struct tuple_element<I, array<T, N>>; 1050b57cec5SDimitry Andrictemplate <size_t I, class T, size_t N> T& get(array<T, N>&) noexcept; // constexpr in C++14 1060b57cec5SDimitry Andrictemplate <size_t I, class T, size_t N> const T& get(const array<T, N>&) noexcept; // constexpr in C++14 1070b57cec5SDimitry Andrictemplate <size_t I, class T, size_t N> T&& get(array<T, N>&&) noexcept; // constexpr in C++14 1080b57cec5SDimitry Andrictemplate <size_t I, class T, size_t N> const T&& get(const array<T, N>&&) noexcept; // constexpr in C++14 1090b57cec5SDimitry Andric 1100b57cec5SDimitry Andric} // std 1110b57cec5SDimitry Andric 1120b57cec5SDimitry Andric*/ 1130b57cec5SDimitry Andric 11481ad6265SDimitry Andric#include <__algorithm/equal.h> 11581ad6265SDimitry Andric#include <__algorithm/fill_n.h> 11681ad6265SDimitry Andric#include <__algorithm/lexicographical_compare.h> 11706c3fb27SDimitry Andric#include <__algorithm/lexicographical_compare_three_way.h> 11881ad6265SDimitry Andric#include <__algorithm/swap_ranges.h> 11981ad6265SDimitry Andric#include <__assert> // all public C++ headers provide the assertion handler 1200b57cec5SDimitry Andric#include <__config> 12106c3fb27SDimitry Andric#include <__fwd/array.h> 12281ad6265SDimitry Andric#include <__iterator/reverse_iterator.h> 12306c3fb27SDimitry Andric#include <__tuple/sfinae_helpers.h> 12406c3fb27SDimitry Andric#include <__type_traits/conditional.h> 12506c3fb27SDimitry Andric#include <__type_traits/is_array.h> 12606c3fb27SDimitry Andric#include <__type_traits/is_const.h> 12706c3fb27SDimitry Andric#include <__type_traits/is_constructible.h> 12806c3fb27SDimitry Andric#include <__type_traits/is_move_constructible.h> 12906c3fb27SDimitry Andric#include <__type_traits/is_nothrow_constructible.h> 13006c3fb27SDimitry Andric#include <__type_traits/is_nothrow_move_constructible.h> 13106c3fb27SDimitry Andric#include <__type_traits/is_same.h> 13206c3fb27SDimitry Andric#include <__type_traits/is_swappable.h> 13306c3fb27SDimitry Andric#include <__type_traits/remove_cv.h> 1345f757f3fSDimitry Andric#include <__utility/empty.h> 13581ad6265SDimitry Andric#include <__utility/integer_sequence.h> 13681ad6265SDimitry Andric#include <__utility/move.h> 13781ad6265SDimitry Andric#include <__utility/unreachable.h> 138fe6060f1SDimitry Andric#include <stdexcept> 1390b57cec5SDimitry Andric#include <version> 1400b57cec5SDimitry Andric 14181ad6265SDimitry Andric// standard-mandated includes 14281ad6265SDimitry Andric 14381ad6265SDimitry Andric// [iterator.range] 14481ad6265SDimitry Andric#include <__iterator/access.h> 14581ad6265SDimitry Andric#include <__iterator/data.h> 14681ad6265SDimitry Andric#include <__iterator/empty.h> 14781ad6265SDimitry Andric#include <__iterator/reverse_access.h> 14881ad6265SDimitry Andric#include <__iterator/size.h> 14981ad6265SDimitry Andric 15081ad6265SDimitry Andric// [array.syn] 15181ad6265SDimitry Andric#include <compare> 15281ad6265SDimitry Andric#include <initializer_list> 15381ad6265SDimitry Andric 154bdd1243dSDimitry Andric// [tuple.helper] 15506c3fb27SDimitry Andric#include <__tuple/tuple_element.h> 15606c3fb27SDimitry Andric#include <__tuple/tuple_size.h> 157bdd1243dSDimitry Andric 1580b57cec5SDimitry Andric#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER) 1590b57cec5SDimitry Andric# pragma GCC system_header 1600b57cec5SDimitry Andric#endif 1610b57cec5SDimitry Andric 1620b57cec5SDimitry Andric_LIBCPP_BEGIN_NAMESPACE_STD 1630b57cec5SDimitry Andric 1640b57cec5SDimitry Andrictemplate <class _Tp, size_t _Size> 165*cb14a3feSDimitry Andricstruct _LIBCPP_TEMPLATE_VIS array { 1660b57cec5SDimitry Andric // types: 1675f757f3fSDimitry Andric using __self = array; 1685f757f3fSDimitry Andric using value_type = _Tp; 1695f757f3fSDimitry Andric using reference = value_type&; 1705f757f3fSDimitry Andric using const_reference = const value_type&; 1715f757f3fSDimitry Andric using iterator = value_type*; 1725f757f3fSDimitry Andric using const_iterator = const value_type*; 1735f757f3fSDimitry Andric using pointer = value_type*; 1745f757f3fSDimitry Andric using const_pointer = const value_type*; 1755f757f3fSDimitry Andric using size_type = size_t; 1765f757f3fSDimitry Andric using difference_type = ptrdiff_t; 1775f757f3fSDimitry Andric using reverse_iterator = std::reverse_iterator<iterator>; 1785f757f3fSDimitry Andric using const_reverse_iterator = std::reverse_iterator<const_iterator>; 1790b57cec5SDimitry Andric 1800b57cec5SDimitry Andric _Tp __elems_[_Size]; 1810b57cec5SDimitry Andric 1820b57cec5SDimitry Andric // No explicit construct/copy/destroy for aggregate type 183*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 void fill(const value_type& __u) { 1845f757f3fSDimitry Andric std::fill_n(data(), _Size, __u); 1850b57cec5SDimitry Andric } 1860b57cec5SDimitry Andric 187*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 void swap(array& __a) 188*cb14a3feSDimitry Andric _NOEXCEPT_(__is_nothrow_swappable<_Tp>::value) { 1895f757f3fSDimitry Andric std::swap_ranges(data(), data() + _Size, __a.data()); 1900b57cec5SDimitry Andric } 1910b57cec5SDimitry Andric 1920b57cec5SDimitry Andric // iterators: 193*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 iterator begin() _NOEXCEPT { return iterator(data()); } 194*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_iterator begin() const _NOEXCEPT { 195*cb14a3feSDimitry Andric return const_iterator(data()); 196*cb14a3feSDimitry Andric } 197*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 iterator end() _NOEXCEPT { return iterator(data() + _Size); } 198*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_iterator end() const _NOEXCEPT { 199*cb14a3feSDimitry Andric return const_iterator(data() + _Size); 200*cb14a3feSDimitry Andric } 2010b57cec5SDimitry Andric 202*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 reverse_iterator rbegin() _NOEXCEPT { 203*cb14a3feSDimitry Andric return reverse_iterator(end()); 204*cb14a3feSDimitry Andric } 205*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_reverse_iterator rbegin() const _NOEXCEPT { 206*cb14a3feSDimitry Andric return const_reverse_iterator(end()); 207*cb14a3feSDimitry Andric } 208*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 reverse_iterator rend() _NOEXCEPT { 209*cb14a3feSDimitry Andric return reverse_iterator(begin()); 210*cb14a3feSDimitry Andric } 211*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_reverse_iterator rend() const _NOEXCEPT { 212*cb14a3feSDimitry Andric return const_reverse_iterator(begin()); 213*cb14a3feSDimitry Andric } 2140b57cec5SDimitry Andric 215*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_iterator cbegin() const _NOEXCEPT { return begin(); } 216*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_iterator cend() const _NOEXCEPT { return end(); } 217*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_reverse_iterator crbegin() const _NOEXCEPT { 218*cb14a3feSDimitry Andric return rbegin(); 219*cb14a3feSDimitry Andric } 220*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_reverse_iterator crend() const _NOEXCEPT { return rend(); } 2210b57cec5SDimitry Andric 2220b57cec5SDimitry Andric // capacity: 223*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR size_type size() const _NOEXCEPT { return _Size; } 224*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR size_type max_size() const _NOEXCEPT { return _Size; } 225*cb14a3feSDimitry Andric _LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR bool empty() const _NOEXCEPT { 226*cb14a3feSDimitry Andric return _Size == 0; 227*cb14a3feSDimitry Andric } 2280b57cec5SDimitry Andric 2290b57cec5SDimitry Andric // element access: 230*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 reference operator[](size_type __n) _NOEXCEPT { 23106c3fb27SDimitry Andric _LIBCPP_ASSERT_VALID_ELEMENT_ACCESS(__n < _Size, "out-of-bounds access in std::array<T, N>"); 2325ffd83dbSDimitry Andric return __elems_[__n]; 2335ffd83dbSDimitry Andric } 234*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 const_reference operator[](size_type __n) const _NOEXCEPT { 23506c3fb27SDimitry Andric _LIBCPP_ASSERT_VALID_ELEMENT_ACCESS(__n < _Size, "out-of-bounds access in std::array<T, N>"); 2365ffd83dbSDimitry Andric return __elems_[__n]; 2375ffd83dbSDimitry Andric } 2380b57cec5SDimitry Andric 239*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 reference at(size_type __n) { 2405ffd83dbSDimitry Andric if (__n >= _Size) 2415ffd83dbSDimitry Andric __throw_out_of_range("array::at"); 2425ffd83dbSDimitry Andric return __elems_[__n]; 2435ffd83dbSDimitry Andric } 2440b57cec5SDimitry Andric 245*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 const_reference at(size_type __n) const { 2465ffd83dbSDimitry Andric if (__n >= _Size) 2475ffd83dbSDimitry Andric __throw_out_of_range("array::at"); 2485ffd83dbSDimitry Andric return __elems_[__n]; 2495ffd83dbSDimitry Andric } 2505ffd83dbSDimitry Andric 2515f757f3fSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 reference front() _NOEXCEPT { return (*this)[0]; } 2525f757f3fSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 const_reference front() const _NOEXCEPT { return (*this)[0]; } 2535f757f3fSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 reference back() _NOEXCEPT { return (*this)[_Size - 1]; } 254*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 const_reference back() const _NOEXCEPT { 255*cb14a3feSDimitry Andric return (*this)[_Size - 1]; 256*cb14a3feSDimitry Andric } 2570b57cec5SDimitry Andric 258*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 value_type* data() _NOEXCEPT { return __elems_; } 259*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const value_type* data() const _NOEXCEPT { return __elems_; } 2600b57cec5SDimitry Andric}; 2610b57cec5SDimitry Andric 2620b57cec5SDimitry Andrictemplate <class _Tp> 263*cb14a3feSDimitry Andricstruct _LIBCPP_TEMPLATE_VIS array<_Tp, 0> { 2640b57cec5SDimitry Andric // types: 2650b57cec5SDimitry Andric typedef array __self; 2660b57cec5SDimitry Andric typedef _Tp value_type; 2670b57cec5SDimitry Andric typedef value_type& reference; 2680b57cec5SDimitry Andric typedef const value_type& const_reference; 2690b57cec5SDimitry Andric typedef value_type* iterator; 2700b57cec5SDimitry Andric typedef const value_type* const_iterator; 2710b57cec5SDimitry Andric typedef value_type* pointer; 2720b57cec5SDimitry Andric typedef const value_type* const_pointer; 2730b57cec5SDimitry Andric typedef size_t size_type; 2740b57cec5SDimitry Andric typedef ptrdiff_t difference_type; 2755f757f3fSDimitry Andric typedef std::reverse_iterator<iterator> reverse_iterator; 2765f757f3fSDimitry Andric typedef std::reverse_iterator<const_iterator> const_reverse_iterator; 2770b57cec5SDimitry Andric 2785f757f3fSDimitry Andric typedef __conditional_t<is_const<_Tp>::value, const __empty, __empty> _EmptyType; 2790b57cec5SDimitry Andric 280*cb14a3feSDimitry Andric struct _ArrayInStructT { 281*cb14a3feSDimitry Andric _Tp __data_[1]; 282*cb14a3feSDimitry Andric }; 2835f757f3fSDimitry Andric _ALIGNAS_TYPE(_ArrayInStructT) _EmptyType __elems_[sizeof(_ArrayInStructT)]; 2840b57cec5SDimitry Andric 285*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 value_type* data() _NOEXCEPT { return nullptr; } 286*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const value_type* data() const _NOEXCEPT { return nullptr; } 2875ffd83dbSDimitry Andric 2880b57cec5SDimitry Andric // No explicit construct/copy/destroy for aggregate type 289*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 void fill(const value_type&) { 290*cb14a3feSDimitry Andric static_assert(!is_const<_Tp>::value, "cannot fill zero-sized array of type 'const T'"); 2910b57cec5SDimitry Andric } 2920b57cec5SDimitry Andric 293*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 void swap(array&) _NOEXCEPT { 294*cb14a3feSDimitry Andric static_assert(!is_const<_Tp>::value, "cannot swap zero-sized array of type 'const T'"); 2950b57cec5SDimitry Andric } 2960b57cec5SDimitry Andric 2970b57cec5SDimitry Andric // iterators: 298*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 iterator begin() _NOEXCEPT { return iterator(data()); } 299*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_iterator begin() const _NOEXCEPT { 300*cb14a3feSDimitry Andric return const_iterator(data()); 301*cb14a3feSDimitry Andric } 302*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 iterator end() _NOEXCEPT { return iterator(data()); } 303*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_iterator end() const _NOEXCEPT { 304*cb14a3feSDimitry Andric return const_iterator(data()); 305*cb14a3feSDimitry Andric } 3060b57cec5SDimitry Andric 307*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 reverse_iterator rbegin() _NOEXCEPT { 308*cb14a3feSDimitry Andric return reverse_iterator(end()); 309*cb14a3feSDimitry Andric } 310*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_reverse_iterator rbegin() const _NOEXCEPT { 311*cb14a3feSDimitry Andric return const_reverse_iterator(end()); 312*cb14a3feSDimitry Andric } 313*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 reverse_iterator rend() _NOEXCEPT { 314*cb14a3feSDimitry Andric return reverse_iterator(begin()); 315*cb14a3feSDimitry Andric } 316*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_reverse_iterator rend() const _NOEXCEPT { 317*cb14a3feSDimitry Andric return const_reverse_iterator(begin()); 318*cb14a3feSDimitry Andric } 3190b57cec5SDimitry Andric 320*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_iterator cbegin() const _NOEXCEPT { return begin(); } 321*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_iterator cend() const _NOEXCEPT { return end(); } 322*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_reverse_iterator crbegin() const _NOEXCEPT { 323*cb14a3feSDimitry Andric return rbegin(); 324*cb14a3feSDimitry Andric } 325*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 const_reverse_iterator crend() const _NOEXCEPT { return rend(); } 3260b57cec5SDimitry Andric 3270b57cec5SDimitry Andric // capacity: 328*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR size_type size() const _NOEXCEPT { return 0; } 329*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR size_type max_size() const _NOEXCEPT { return 0; } 330*cb14a3feSDimitry Andric _LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR bool empty() const _NOEXCEPT { return true; } 3310b57cec5SDimitry Andric 3320b57cec5SDimitry Andric // element access: 333*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 reference operator[](size_type) _NOEXCEPT { 33406c3fb27SDimitry Andric _LIBCPP_ASSERT_VALID_ELEMENT_ACCESS(false, "cannot call array<T, 0>::operator[] on a zero-sized array"); 33581ad6265SDimitry Andric __libcpp_unreachable(); 3360b57cec5SDimitry Andric } 3370b57cec5SDimitry Andric 338*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 const_reference operator[](size_type) const _NOEXCEPT { 33906c3fb27SDimitry Andric _LIBCPP_ASSERT_VALID_ELEMENT_ACCESS(false, "cannot call array<T, 0>::operator[] on a zero-sized array"); 34081ad6265SDimitry Andric __libcpp_unreachable(); 3410b57cec5SDimitry Andric } 3420b57cec5SDimitry Andric 343*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 reference at(size_type) { 3440b57cec5SDimitry Andric __throw_out_of_range("array<T, 0>::at"); 34581ad6265SDimitry Andric __libcpp_unreachable(); 3460b57cec5SDimitry Andric } 3470b57cec5SDimitry Andric 348*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 const_reference at(size_type) const { 3490b57cec5SDimitry Andric __throw_out_of_range("array<T, 0>::at"); 35081ad6265SDimitry Andric __libcpp_unreachable(); 3510b57cec5SDimitry Andric } 3520b57cec5SDimitry Andric 353*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 reference front() _NOEXCEPT { 35406c3fb27SDimitry Andric _LIBCPP_ASSERT_VALID_ELEMENT_ACCESS(false, "cannot call array<T, 0>::front() on a zero-sized array"); 35581ad6265SDimitry Andric __libcpp_unreachable(); 3560b57cec5SDimitry Andric } 3570b57cec5SDimitry Andric 358*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 const_reference front() const _NOEXCEPT { 35906c3fb27SDimitry Andric _LIBCPP_ASSERT_VALID_ELEMENT_ACCESS(false, "cannot call array<T, 0>::front() on a zero-sized array"); 36081ad6265SDimitry Andric __libcpp_unreachable(); 3610b57cec5SDimitry Andric } 3620b57cec5SDimitry Andric 363*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 reference back() _NOEXCEPT { 36406c3fb27SDimitry Andric _LIBCPP_ASSERT_VALID_ELEMENT_ACCESS(false, "cannot call array<T, 0>::back() on a zero-sized array"); 36581ad6265SDimitry Andric __libcpp_unreachable(); 3660b57cec5SDimitry Andric } 3670b57cec5SDimitry Andric 368*cb14a3feSDimitry Andric _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 const_reference back() const _NOEXCEPT { 36906c3fb27SDimitry Andric _LIBCPP_ASSERT_VALID_ELEMENT_ACCESS(false, "cannot call array<T, 0>::back() on a zero-sized array"); 37081ad6265SDimitry Andric __libcpp_unreachable(); 3710b57cec5SDimitry Andric } 3720b57cec5SDimitry Andric}; 3730b57cec5SDimitry Andric 37406c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 17 375*cb14a3feSDimitry Andrictemplate <class _Tp, class... _Args, class = enable_if_t<__all<_IsSame<_Tp, _Args>::value...>::value> > 376*cb14a3feSDimitry Andricarray(_Tp, _Args...) -> array<_Tp, 1 + sizeof...(_Args)>; 3770b57cec5SDimitry Andric#endif 3780b57cec5SDimitry Andric 3790b57cec5SDimitry Andrictemplate <class _Tp, size_t _Size> 380*cb14a3feSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 bool 381*cb14a3feSDimitry Andricoperator==(const array<_Tp, _Size>& __x, const array<_Tp, _Size>& __y) { 3825f757f3fSDimitry Andric return std::equal(__x.begin(), __x.end(), __y.begin()); 3830b57cec5SDimitry Andric} 3840b57cec5SDimitry Andric 38506c3fb27SDimitry Andric#if _LIBCPP_STD_VER <= 17 38606c3fb27SDimitry Andric 3870b57cec5SDimitry Andrictemplate <class _Tp, size_t _Size> 38806c3fb27SDimitry Andricinline _LIBCPP_HIDE_FROM_ABI bool operator!=(const array<_Tp, _Size>& __x, const array<_Tp, _Size>& __y) { 3890b57cec5SDimitry Andric return !(__x == __y); 3900b57cec5SDimitry Andric} 3910b57cec5SDimitry Andric 3920b57cec5SDimitry Andrictemplate <class _Tp, size_t _Size> 39306c3fb27SDimitry Andricinline _LIBCPP_HIDE_FROM_ABI bool operator<(const array<_Tp, _Size>& __x, const array<_Tp, _Size>& __y) { 3945f757f3fSDimitry Andric return std::lexicographical_compare(__x.begin(), __x.end(), __y.begin(), __y.end()); 3950b57cec5SDimitry Andric} 3960b57cec5SDimitry Andric 3970b57cec5SDimitry Andrictemplate <class _Tp, size_t _Size> 39806c3fb27SDimitry Andricinline _LIBCPP_HIDE_FROM_ABI bool operator>(const array<_Tp, _Size>& __x, const array<_Tp, _Size>& __y) { 3990b57cec5SDimitry Andric return __y < __x; 4000b57cec5SDimitry Andric} 4010b57cec5SDimitry Andric 4020b57cec5SDimitry Andrictemplate <class _Tp, size_t _Size> 40306c3fb27SDimitry Andricinline _LIBCPP_HIDE_FROM_ABI bool operator<=(const array<_Tp, _Size>& __x, const array<_Tp, _Size>& __y) { 4040b57cec5SDimitry Andric return !(__y < __x); 4050b57cec5SDimitry Andric} 4060b57cec5SDimitry Andric 4070b57cec5SDimitry Andrictemplate <class _Tp, size_t _Size> 40806c3fb27SDimitry Andricinline _LIBCPP_HIDE_FROM_ABI bool operator>=(const array<_Tp, _Size>& __x, const array<_Tp, _Size>& __y) { 4090b57cec5SDimitry Andric return !(__x < __y); 4100b57cec5SDimitry Andric} 4110b57cec5SDimitry Andric 41206c3fb27SDimitry Andric#else // _LIBCPP_STD_VER <= 17 41306c3fb27SDimitry Andric 41406c3fb27SDimitry Andrictemplate <class _Tp, size_t _Size> 41506c3fb27SDimitry Andric_LIBCPP_HIDE_FROM_ABI constexpr __synth_three_way_result<_Tp> 41606c3fb27SDimitry Andricoperator<=>(const array<_Tp, _Size>& __x, const array<_Tp, _Size>& __y) { 41706c3fb27SDimitry Andric return std::lexicographical_compare_three_way( 41806c3fb27SDimitry Andric __x.begin(), __x.end(), __y.begin(), __y.end(), std::__synth_three_way<_Tp, _Tp>); 41906c3fb27SDimitry Andric} 42006c3fb27SDimitry Andric 42106c3fb27SDimitry Andric#endif // _LIBCPP_STD_VER <= 17 42206c3fb27SDimitry Andric 4235f757f3fSDimitry Andrictemplate <class _Tp, size_t _Size, __enable_if_t<_Size == 0 || __is_swappable<_Tp>::value, int> = 0> 424*cb14a3feSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 void swap(array<_Tp, _Size>& __x, array<_Tp, _Size>& __y) 425*cb14a3feSDimitry Andric _NOEXCEPT_(noexcept(__x.swap(__y))) { 4260b57cec5SDimitry Andric __x.swap(__y); 4270b57cec5SDimitry Andric} 4280b57cec5SDimitry Andric 4290b57cec5SDimitry Andrictemplate <class _Tp, size_t _Size> 430*cb14a3feSDimitry Andricstruct _LIBCPP_TEMPLATE_VIS tuple_size<array<_Tp, _Size> > : public integral_constant<size_t, _Size> {}; 4310b57cec5SDimitry Andric 4320b57cec5SDimitry Andrictemplate <size_t _Ip, class _Tp, size_t _Size> 433*cb14a3feSDimitry Andricstruct _LIBCPP_TEMPLATE_VIS tuple_element<_Ip, array<_Tp, _Size> > { 4340b57cec5SDimitry Andric static_assert(_Ip < _Size, "Index out of bounds in std::tuple_element<> (std::array)"); 4350b57cec5SDimitry Andric typedef _Tp type; 4360b57cec5SDimitry Andric}; 4370b57cec5SDimitry Andric 4380b57cec5SDimitry Andrictemplate <size_t _Ip, class _Tp, size_t _Size> 439*cb14a3feSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 _Tp& get(array<_Tp, _Size>& __a) _NOEXCEPT { 4400b57cec5SDimitry Andric static_assert(_Ip < _Size, "Index out of bounds in std::get<> (std::array)"); 4410b57cec5SDimitry Andric return __a.__elems_[_Ip]; 4420b57cec5SDimitry Andric} 4430b57cec5SDimitry Andric 4440b57cec5SDimitry Andrictemplate <size_t _Ip, class _Tp, size_t _Size> 445*cb14a3feSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 const _Tp& get(const array<_Tp, _Size>& __a) _NOEXCEPT { 4460b57cec5SDimitry Andric static_assert(_Ip < _Size, "Index out of bounds in std::get<> (const std::array)"); 4470b57cec5SDimitry Andric return __a.__elems_[_Ip]; 4480b57cec5SDimitry Andric} 4490b57cec5SDimitry Andric 4500b57cec5SDimitry Andrictemplate <size_t _Ip, class _Tp, size_t _Size> 451*cb14a3feSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 _Tp&& get(array<_Tp, _Size>&& __a) _NOEXCEPT { 4520b57cec5SDimitry Andric static_assert(_Ip < _Size, "Index out of bounds in std::get<> (std::array &&)"); 4535f757f3fSDimitry Andric return std::move(__a.__elems_[_Ip]); 4540b57cec5SDimitry Andric} 4550b57cec5SDimitry Andric 4560b57cec5SDimitry Andrictemplate <size_t _Ip, class _Tp, size_t _Size> 457*cb14a3feSDimitry Andricinline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 const _Tp&& get(const array<_Tp, _Size>&& __a) _NOEXCEPT { 4580b57cec5SDimitry Andric static_assert(_Ip < _Size, "Index out of bounds in std::get<> (const std::array &&)"); 4595f757f3fSDimitry Andric return std::move(__a.__elems_[_Ip]); 4600b57cec5SDimitry Andric} 4610b57cec5SDimitry Andric 46206c3fb27SDimitry Andric#if _LIBCPP_STD_VER >= 20 4635ffd83dbSDimitry Andric 4645ffd83dbSDimitry Andrictemplate <typename _Tp, size_t _Size, size_t... _Index> 4655f757f3fSDimitry Andric_LIBCPP_HIDE_FROM_ABI constexpr array<remove_cv_t<_Tp>, _Size> 4665ffd83dbSDimitry Andric__to_array_lvalue_impl(_Tp (&__arr)[_Size], index_sequence<_Index...>) { 4675ffd83dbSDimitry Andric return {{__arr[_Index]...}}; 4685ffd83dbSDimitry Andric} 4695ffd83dbSDimitry Andric 4705ffd83dbSDimitry Andrictemplate <typename _Tp, size_t _Size, size_t... _Index> 4715f757f3fSDimitry Andric_LIBCPP_HIDE_FROM_ABI constexpr array<remove_cv_t<_Tp>, _Size> 4725ffd83dbSDimitry Andric__to_array_rvalue_impl(_Tp (&&__arr)[_Size], index_sequence<_Index...>) { 4735f757f3fSDimitry Andric return {{std::move(__arr[_Index])...}}; 4745ffd83dbSDimitry Andric} 4755ffd83dbSDimitry Andric 4765ffd83dbSDimitry Andrictemplate <typename _Tp, size_t _Size> 4775f757f3fSDimitry Andric_LIBCPP_HIDE_FROM_ABI constexpr array<remove_cv_t<_Tp>, _Size> 4785ffd83dbSDimitry Andricto_array(_Tp (&__arr)[_Size]) noexcept(is_nothrow_constructible_v<_Tp, _Tp&>) { 479*cb14a3feSDimitry Andric static_assert(!is_array_v<_Tp>, "[array.creation]/1: to_array does not accept multidimensional arrays."); 480*cb14a3feSDimitry Andric static_assert(is_constructible_v<_Tp, _Tp&>, "[array.creation]/1: to_array requires copy constructible elements."); 4815f757f3fSDimitry Andric return std::__to_array_lvalue_impl(__arr, make_index_sequence<_Size>()); 4825ffd83dbSDimitry Andric} 4835ffd83dbSDimitry Andric 4845ffd83dbSDimitry Andrictemplate <typename _Tp, size_t _Size> 4855f757f3fSDimitry Andric_LIBCPP_HIDE_FROM_ABI constexpr array<remove_cv_t<_Tp>, _Size> 4865ffd83dbSDimitry Andricto_array(_Tp (&&__arr)[_Size]) noexcept(is_nothrow_move_constructible_v<_Tp>) { 487*cb14a3feSDimitry Andric static_assert(!is_array_v<_Tp>, "[array.creation]/4: to_array does not accept multidimensional arrays."); 488*cb14a3feSDimitry Andric static_assert(is_move_constructible_v<_Tp>, "[array.creation]/4: to_array requires move constructible elements."); 489*cb14a3feSDimitry Andric return std::__to_array_rvalue_impl(std::move(__arr), make_index_sequence<_Size>()); 4905ffd83dbSDimitry Andric} 4915ffd83dbSDimitry Andric 49206c3fb27SDimitry Andric#endif // _LIBCPP_STD_VER >= 20 4935ffd83dbSDimitry Andric 4940b57cec5SDimitry Andric_LIBCPP_END_NAMESPACE_STD 4950b57cec5SDimitry Andric 496bdd1243dSDimitry Andric#if !defined(_LIBCPP_REMOVE_TRANSITIVE_INCLUDES) && _LIBCPP_STD_VER <= 20 497bdd1243dSDimitry Andric# include <algorithm> 498bdd1243dSDimitry Andric# include <concepts> 49906c3fb27SDimitry Andric# include <cstdlib> 500bdd1243dSDimitry Andric# include <iterator> 50106c3fb27SDimitry Andric# include <type_traits> 502bdd1243dSDimitry Andric# include <utility> 503bdd1243dSDimitry Andric#endif 504bdd1243dSDimitry Andric 5050b57cec5SDimitry Andric#endif // _LIBCPP_ARRAY 506