LCOV - code coverage report
Current view: top level - json - array.hpp (source / functions) Coverage Total Hit
Test: coverage_filtered.info Lines: 100.0 % 29 29
Test Date: 2026-01-06 06:25:55 Functions: 100.0 % 9 9

            Line data    Source code
       1              : //
       2              : // Copyright (c) 2019 Vinnie Falco (vinnie.falco@gmail.com)
       3              : //
       4              : // Distributed under the Boost Software License, Version 1.0. (See accompanying
       5              : // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
       6              : //
       7              : // Official repository: https://github.com/boostorg/json
       8              : //
       9              : 
      10              : #ifndef BOOST_JSON_ARRAY_HPP
      11              : #define BOOST_JSON_ARRAY_HPP
      12              : 
      13              : #include <boost/json/detail/config.hpp>
      14              : #include <boost/json/detail/array.hpp>
      15              : #include <boost/json/kind.hpp>
      16              : #include <boost/json/pilfer.hpp>
      17              : #include <boost/json/storage_ptr.hpp>
      18              : #include <boost/system/result.hpp>
      19              : #include <cstdlib>
      20              : #include <initializer_list>
      21              : #include <iterator>
      22              : 
      23              : namespace boost {
      24              : namespace json {
      25              : 
      26              : #ifndef BOOST_JSON_DOCS
      27              : class value;
      28              : class value_ref;
      29              : #endif
      30              : 
      31              : /** A dynamically sized array of JSON values
      32              : 
      33              :     This is the type used to represent a JSON array as a modifiable container.
      34              :     The interface and performance characteristics are modeled after
      35              :     `std::vector<value>`.
      36              : 
      37              :     Elements are stored contiguously, which means that they can be accessed not
      38              :     only through iterators, but also using offsets to regular pointers to
      39              :     elements. A pointer to an element of an `array` may be passed to any
      40              :     function that expects a pointer to @ref value.
      41              : 
      42              :     The storage of the array is handled automatically, being expanded and
      43              :     contracted as needed. Arrays usually occupy more space than array language
      44              :     constructs, because more memory is allocated to handle future growth. This
      45              :     way an array does not need to reallocate each time an element is inserted,
      46              :     but only when the additional memory is used up. The total amount of
      47              :     allocated memory can be queried using the @ref capacity function. Extra
      48              :     memory can be relinquished by calling @ref shrink_to_fit.
      49              : 
      50              : 
      51              :     Reallocations are usually costly operations in terms of performance. The
      52              :     @ref reserve function can be used to eliminate reallocations if the number
      53              :     of elements is known beforehand.
      54              : 
      55              :     The complexity (efficiency) of common operations on arrays is as follows:
      56              : 
      57              :     @li Random access---constant *O(1)*.
      58              :     @li Insertion or removal of elements at the end - amortized
      59              :         constant *O(1)*.
      60              :     @li Insertion or removal of elements---linear in the distance to the end of
      61              :         the array *O(n)*.
      62              : 
      63              :     @par Allocators
      64              : 
      65              :     All elements stored in the container, and their children if any, will use
      66              :     the same memory resource that was used to construct the container.
      67              : 
      68              :     @par Thread Safety
      69              : 
      70              :     Non-const member functions may not be called concurrently with any other
      71              :     member functions.
      72              : 
      73              :     @par Satisfies
      74              :         [*ContiguousContainer*](https://en.cppreference.com/w/cpp/named_req/ContiguousContainer),
      75              :         [*ReversibleContainer*](https://en.cppreference.com/w/cpp/named_req/ReversibleContainer), and
      76              :         {req_SequenceContainer}.
      77              : */
      78              : class array
      79              : {
      80              :     struct table;
      81              :     class revert_construct;
      82              :     class revert_insert;
      83              :     friend class value;
      84              : 
      85              :     storage_ptr sp_;        // must come first
      86              :     kind k_ = kind::array;  // must come second
      87              :     table* t_;
      88              : 
      89              :     BOOST_JSON_DECL
      90              :     static table empty_;
      91              : 
      92              :     inline
      93              :     static
      94              :     void
      95              :     relocate(
      96              :         value* dest,
      97              :         value* src,
      98              :         std::size_t n) noexcept;
      99              : 
     100              :     inline
     101              :     void
     102              :     destroy(
     103              :         value* first,
     104              :         value* last) noexcept;
     105              : 
     106              :     BOOST_JSON_DECL
     107              :     void
     108              :     destroy() noexcept;
     109              : 
     110              :     BOOST_JSON_DECL
     111              :     explicit
     112              :     array(detail::unchecked_array&& ua);
     113              : 
     114              : public:
     115              :     /// Associated [Allocator](https://en.cppreference.com/w/cpp/named_req/Allocator)
     116              :     using allocator_type = container::pmr::polymorphic_allocator<value>;
     117              : 
     118              :     /// The type used to represent unsigned integers
     119              :     using size_type = std::size_t;
     120              : 
     121              :     /// The type of each element
     122              :     using value_type = value;
     123              : 
     124              :     /// The type used to represent signed integers
     125              :     using difference_type = std::ptrdiff_t;
     126              : 
     127              :     /// A reference to an element
     128              :     using reference = value&;
     129              : 
     130              :     /// A const reference to an element
     131              :     using const_reference = value const&;
     132              : 
     133              :     /// A pointer to an element
     134              :     using pointer = value*;
     135              : 
     136              :     /// A const pointer to an element
     137              :     using const_pointer = value const*;
     138              : 
     139              :     /// A random access iterator to an element
     140              :     using iterator = value*;
     141              : 
     142              :     /// A random access const iterator to an element
     143              :     using const_iterator = value const*;
     144              : 
     145              :     /// A reverse random access iterator to an element
     146              :     using reverse_iterator =
     147              :         std::reverse_iterator<iterator>;
     148              : 
     149              :     /// A reverse random access const iterator to an element
     150              :     using const_reverse_iterator =
     151              :         std::reverse_iterator<const_iterator>;
     152              : 
     153              :     //------------------------------------------------------
     154              : 
     155              :     /** Destructor.
     156              : 
     157              :         The destructor for each element is called if needed, any used memory is
     158              :         deallocated, and shared ownership of the
     159              :         @ref boost::container::pmr::memory_resource is released.
     160              : 
     161              :         @par Complexity
     162              :         Linear in @ref size().
     163              : 
     164              :         @par Exception Safety
     165              :         No-throw guarantee.
     166              :     */
     167              :     BOOST_JSON_DECL
     168              :     ~array() noexcept;
     169              : 
     170              :     //------------------------------------------------------
     171              : 
     172              :     /** Constructors.
     173              : 
     174              :         Constructs an array.
     175              : 
     176              :         @li **(1)**, **(2)**  the array is empty and has zero capacity.
     177              : 
     178              :         @li **(3)** the array is filled with `count` copies of `jv`.
     179              : 
     180              :         @li **(4)** the array is filled with `count` null values.
     181              : 
     182              :         @li **(5)** the array is filled with values in the range
     183              :             `[first, last)`, preserving order.
     184              : 
     185              :         @li **(6)** the array is filled with copies of the values in `init`,
     186              :             preserving order.
     187              : 
     188              :         @li **(7)**, **(8)** the array is filled with copies of the elements of
     189              :             `other`, preserving order.
     190              : 
     191              :         @li **(9)** the array acquires ownership of the contents of `other`.
     192              : 
     193              :         @li **(10)** equivalent to **(9)** if `*sp == *other.storage()`;
     194              :             otherwise equivalent to **(8)**.
     195              : 
     196              :         @li **(11)** the array acquires ownership of the contents of `other`
     197              :             using pilfer semantics. This is more efficient than move
     198              :             construction, when it is known that the moved-from object will be
     199              :             immediately destroyed afterwards.
     200              : 
     201              :         With **(2)**, **(4)**, **(5)**, **(6)**, **(8)**, **(10)** the
     202              :         constructed array uses memory resource of `sp`. With **(7)**, **(9)**,
     203              :         and **(11)** it uses `other`'s memory resource. In either case the
     204              :         array will share the ownership of the memory resource. With **(1)**
     205              :         and **(3)** it uses the
     206              :         \<\<default_memory_resource, default memory resource\>\>.
     207              : 
     208              :         After **(9)** `other` behaves as if newly constructed with its
     209              :         current storage pointer.
     210              : 
     211              :         After **(11)** `other` is not in a usable state and may only be
     212              :         destroyed.
     213              : 
     214              :         @par Constraints
     215              : 
     216              :         @code
     217              :         std::is_constructible_v<value, std::iterator_traits<InputIt>::reference>
     218              :         @endcode
     219              : 
     220              :         @par Complexity
     221              :         @li **(1)**, **(2)**, **(9)**, **(11)** constant.
     222              :         @li **(3)**, **(4)** linear in `count`.
     223              :         @li **(5)** linear in `std::distance(first, last)`
     224              :         @li **(6)** linear in `init.size()`.
     225              :         @li **(7)**, **(8)** linear in `other.size()`.
     226              :         @li **(10)** constant if `*sp == *other.storage()`; otherwise linear in
     227              :             `other.size()`.
     228              : 
     229              :         @par Exception Safety
     230              :         @li **(1)**, **(2)**, **(9)**, **(11)** no-throw guarantee.
     231              :         @li **(3)**, **(4)**, **(6)**--**(8)**, **(10)** strong
     232              :             guarantee.
     233              :         @li **(5)** strong guarantee if `InputIt` satisfies
     234              :         {req_ForwardIterator}, basic guarantee otherwise.
     235              : 
     236              :         Calls to `memory_resource::allocate` may throw.
     237              : 
     238              :         @see @ref pilfer,
     239              :             [Valueless Variants Considered Harmful](http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2016/p0308r0.html).
     240              :         @{
     241              :     */
     242           79 :     array() noexcept
     243           79 :         : t_(&empty_)
     244              :     {
     245           79 :     }
     246              : 
     247              :     /** Overload
     248              :         @param sp A pointer to the @ref boost::container::pmr::memory_resource
     249              :         to use. The container will acquire shared ownership of the memory
     250              :         resource.
     251              :     */
     252              :     explicit
     253          644 :     array(storage_ptr sp) noexcept
     254          644 :         : sp_(std::move(sp))
     255          644 :         , k_(kind::array)
     256          644 :         , t_(&empty_)
     257              :     {
     258          644 :     }
     259              : 
     260              :     /** Overload
     261              :         @param count The number of copies to insert.
     262              :         @param jv The value to be inserted.
     263              :         @param sp
     264              :     */
     265              :     BOOST_JSON_DECL
     266              :     array(
     267              :         std::size_t count,
     268              :         value const& jv,
     269              :         storage_ptr sp = {});
     270              : 
     271              :     /// Overload
     272              :     BOOST_JSON_DECL
     273              :     array(
     274              :         std::size_t count,
     275              :         storage_ptr sp = {});
     276              : 
     277              :     /** Overload
     278              : 
     279              :         @param first An input iterator pointing to the first element to insert,
     280              :                or pointing to the end of the range.
     281              :         @param last An input iterator pointing to the end of the range.
     282              :         @param sp
     283              : 
     284              :         @tparam InputIt a type satisfying the {req_InputIterator} requirement.
     285              :     */
     286              :     template<
     287              :         class InputIt
     288              :     #ifndef BOOST_JSON_DOCS
     289              :         ,class = typename std::enable_if<
     290              :             std::is_constructible<value,
     291              :                 typename std::iterator_traits<
     292              :                     InputIt>::reference>::value>::type
     293              :     #endif
     294              :     >
     295              :     array(
     296              :         InputIt first, InputIt last,
     297              :         storage_ptr sp = {});
     298              : 
     299              :     /** Overload
     300              :         @param init The initializer list with elements to insert.
     301              :         @param sp
     302              :     */
     303              :     BOOST_JSON_DECL
     304              :     array(
     305              :         std::initializer_list<value_ref> init,
     306              :         storage_ptr sp = {});
     307              : 
     308              :     /** Overload
     309              :         @param other Another array.
     310              :     */
     311              :     BOOST_JSON_DECL
     312              :     array(array const& other);
     313              : 
     314              :     /// Overload
     315              :     BOOST_JSON_DECL
     316              :     array(
     317              :         array const& other,
     318              :         storage_ptr sp);
     319              : 
     320              :     /// Overload
     321          188 :     array(array&& other) noexcept
     322          188 :         : sp_(other.sp_)
     323          376 :         , t_(detail::exchange(
     324          188 :             other.t_, &empty_))
     325              :     {
     326          188 :     }
     327              : 
     328              :     /// Overload
     329              :     BOOST_JSON_DECL
     330              :     array(
     331              :         array&& other,
     332              :         storage_ptr sp);
     333              : 
     334              :     /// Overload
     335            6 :     array(pilfered<array> other) noexcept
     336            6 :         : sp_(std::move(other.get().sp_))
     337           12 :         , t_(detail::exchange(
     338            6 :             other.get().t_, &empty_))
     339              :     {
     340            6 :     }
     341              :     /// @}
     342              : 
     343              :     /** Assignment operators.
     344              : 
     345              :         Replaces the contents of the array.
     346              :         @li **(1)** the contents are replaced with an element-wise copy of
     347              :             `other`.
     348              :         @li **(2)** takes ownership of `other`'s element storage if
     349              :             `*storage() == *other.storage()`; otherwise equivalent to **(1)**.
     350              :         @li **(3)** the contents are replaced with a copy of the values in
     351              :             `init`.
     352              : 
     353              :         After **(2)**, the moved-from array behaves as if newly constructed
     354              :         with its current storage pointer.
     355              : 
     356              :         @par Complexity
     357              :         @li **(1)** linear in `size() + other.size()`.
     358              :         @li **(2)** constant if `*storage() == *other.storage()`; otherwise
     359              :             linear in `size() + other.size()`.
     360              :         @li **(1)** linear in `size() + init.size()`.
     361              : 
     362              :         @par Exception Safety
     363              :         {sp} **(2)** provides strong guarantee if
     364              :         `*storage() != *other.storage()` and no-throw guarantee otherwise.
     365              :         Other overloads provide strong guarantee.
     366              :         Calls to `memory_resource::allocate` may throw.
     367              : 
     368              :         @param other The array to copy.
     369              : 
     370              :         @return `*this`
     371              : 
     372              :         @{
     373              :     */
     374              :     BOOST_JSON_DECL
     375              :     array&
     376              :     operator=(array const& other);
     377              : 
     378              :     /** Overload
     379              :         @param other The array to move.
     380              :     */
     381              :     BOOST_JSON_DECL
     382              :     array&
     383              :     operator=(array&& other);
     384              : 
     385              :     /** Overload
     386              :         @param init The initializer list to copy.
     387              :     */
     388              :     BOOST_JSON_DECL
     389              :     array&
     390              :     operator=(
     391              :         std::initializer_list<value_ref> init);
     392              :     /// @}
     393              : 
     394              :     /** Return the associated memory resource.
     395              : 
     396              :         This function returns a smart pointer to the
     397              :         @ref boost::container::pmr::memory_resource used by the container.
     398              : 
     399              :         @par Complexity
     400              :         Constant.
     401              : 
     402              :         @par Exception Safety
     403              :         No-throw guarantee.
     404              :     */
     405              :     storage_ptr const&
     406        15208 :     storage() const noexcept
     407              :     {
     408        15208 :         return sp_;
     409              :     }
     410              : 
     411              :     /** Return the associated allocator.
     412              : 
     413              :         This function returns an instance of @ref allocator_type constructed
     414              :         from the associated @ref boost::container::pmr::memory_resource.
     415              : 
     416              :         @par Complexity
     417              :         Constant.
     418              : 
     419              :         @par Exception Safety
     420              :         No-throw guarantee.
     421              :     */
     422              :     allocator_type
     423            1 :     get_allocator() const noexcept
     424              :     {
     425            1 :         return sp_.get();
     426              :     }
     427              : 
     428              :     //------------------------------------------------------
     429              :     //
     430              :     // Element access
     431              :     //
     432              :     //------------------------------------------------------
     433              : 
     434              :     /** Access an element, with bounds checking.
     435              : 
     436              :         Returns @ref boost::system::result containing a reference to the
     437              :         element specified at location `pos`, if `pos` is within the range of
     438              :         the container. Otherwise the result contains an `error_code`.
     439              : 
     440              :         @par Exception Safety
     441              :         No-throw guarantee.
     442              : 
     443              :         @param pos A zero-based index.
     444              : 
     445              :         @par Complexity
     446              :         Constant.
     447              : 
     448              :         @{
     449              :     */
     450              :     BOOST_JSON_DECL
     451              :     system::result<value&>
     452              :     try_at(std::size_t pos) noexcept;
     453              : 
     454              :     BOOST_JSON_DECL
     455              :     system::result<value const&>
     456              :     try_at(std::size_t pos) const noexcept;
     457              :     /// @}
     458              : 
     459              :     /** Access an element, with bounds checking.
     460              : 
     461              :         Returns a reference to the element specified at location `pos`, with
     462              :         bounds checking. If `pos` is not within the range of the container, an
     463              :         exception of type @ref boost::system::system_error is thrown.
     464              : 
     465              :         @par Complexity
     466              :         Constant.
     467              : 
     468              :         @param pos A zero-based index.
     469              : 
     470              :         @param loc `source_location` to use in thrown exception; the source
     471              :             location of the call site by default.
     472              : 
     473              :         @throw `boost::system::system_error` `pos >= size()`.
     474              : 
     475              :         @{
     476              :     */
     477              :     inline
     478              :     value&
     479              :     at(
     480              :         std::size_t pos,
     481              :         source_location const& loc = BOOST_CURRENT_LOCATION) &;
     482              : 
     483              :     inline
     484              :     value&&
     485              :     at(
     486              :         std::size_t pos,
     487              :         source_location const& loc = BOOST_CURRENT_LOCATION) &&;
     488              : 
     489              :     BOOST_JSON_DECL
     490              :     value const&
     491              :     at(
     492              :         std::size_t pos,
     493              :         source_location const& loc = BOOST_CURRENT_LOCATION) const&;
     494              :     /// @}
     495              : 
     496              :     /** Access an element.
     497              : 
     498              :         Returns a reference to the element specified at
     499              :         location `pos`. No bounds checking is performed.
     500              : 
     501              :         @pre `pos < size()`
     502              : 
     503              :         @par Complexity
     504              :         Constant.
     505              : 
     506              :         @param pos A zero-based index
     507              : 
     508              :         @{
     509              :     */
     510              :     inline
     511              :     value&
     512              :     operator[](std::size_t pos) & noexcept;
     513              : 
     514              :     inline
     515              :     value&&
     516              :     operator[](std::size_t pos) && noexcept;
     517              : 
     518              :     inline
     519              :     value const&
     520              :     operator[](std::size_t pos) const& noexcept;
     521              :     /// @}
     522              : 
     523              :     /** Access the first element.
     524              : 
     525              :         Returns a reference to the first element.
     526              : 
     527              :         @pre `! empty()`
     528              : 
     529              :         @par Complexity
     530              :         Constant.
     531              : 
     532              :         @{
     533              :     */
     534              :     inline
     535              :     value&
     536              :     front() & noexcept;
     537              : 
     538              :     inline
     539              :     value&&
     540              :     front() && noexcept;
     541              : 
     542              :     inline
     543              :     value const&
     544              :     front() const& noexcept;
     545              :     /// @}
     546              : 
     547              :     /** Access the last element.
     548              : 
     549              :         Returns a reference to the last element.
     550              : 
     551              :         @pre `!empty()`
     552              : 
     553              :         @par Complexity
     554              :         Constant.
     555              : 
     556              :         @{
     557              :     */
     558              :     inline
     559              :     value&
     560              :     back() & noexcept;
     561              : 
     562              :     inline
     563              :     value&&
     564              :     back() && noexcept;
     565              : 
     566              :     inline
     567              :     value const&
     568              :     back() const& noexcept;
     569              :     /// @}
     570              : 
     571              :     /** Access the underlying array directly.
     572              : 
     573              :         Returns a pointer to the underlying array serving as element storage.
     574              :         The value returned is such that the range `[data(), data() + size())`
     575              :         is always a valid range, even if the container is empty.
     576              : 
     577              :         @note
     578              :         If `size() == 0`, the function may or may not return
     579              :         a null pointer.
     580              : 
     581              :         @par Complexity
     582              :         Constant.
     583              : 
     584              :         @par Exception Safety
     585              :         No-throw guarantee.
     586              : 
     587              :         @{
     588              :     */
     589              :     inline
     590              :     value*
     591              :     data() noexcept;
     592              : 
     593              :     inline
     594              :     value const*
     595              :     data() const noexcept;
     596              :     /// @}
     597              : 
     598              :     /** Return a pointer to an element if it exists.
     599              : 
     600              :         This function returns a pointer to the element at index `pos` when the
     601              :         index is less then the size of the container. Otherwise it returns
     602              :         null.
     603              : 
     604              :         @par Example
     605              :         @code
     606              :         if( auto p = arr.if_contains( 1 ) )
     607              :             std::cout << *p;
     608              :         @endcode
     609              : 
     610              :         @par Complexity
     611              :         Constant.
     612              : 
     613              :         @par Exception Safety
     614              :         No-throw guarantee.
     615              : 
     616              :         @param pos The index of the element to return.
     617              : 
     618              :         @{
     619              :     */
     620              :     inline
     621              :     value const*
     622              :     if_contains(std::size_t pos) const noexcept;
     623              : 
     624              :     inline
     625              :     value*
     626              :     if_contains(std::size_t pos) noexcept;
     627              :     /// @}
     628              : 
     629              :     //------------------------------------------------------
     630              :     //
     631              :     // Iterators
     632              :     //
     633              :     //------------------------------------------------------
     634              : 
     635              :     /** Return an iterator to the first element.
     636              : 
     637              :         If the container is empty, @ref end() is returned.
     638              : 
     639              :         @par Complexity
     640              :         Constant.
     641              : 
     642              :         @par Exception Safety
     643              :         No-throw guarantee.
     644              : 
     645              :         @{
     646              :     */
     647              :     inline
     648              :     iterator
     649              :     begin() noexcept;
     650              : 
     651              :     inline
     652              :     const_iterator
     653              :     begin() const noexcept;
     654              :     /// @}
     655              : 
     656              :     /** Return a const iterator to the first element.
     657              : 
     658              :         If the container is empty, @ref cend() is returned.
     659              : 
     660              :         @par Complexity
     661              :         Constant.
     662              : 
     663              :         @par Exception Safety
     664              :         No-throw guarantee.
     665              :     */
     666              :     inline
     667              :     const_iterator
     668              :     cbegin() const noexcept;
     669              : 
     670              :     /** Return a const iterator past the last element.
     671              : 
     672              :         The returned iterator only acts as a sentinel. Dereferencing it results
     673              :         in undefined behavior.
     674              : 
     675              :         @par Complexity
     676              :         Constant.
     677              : 
     678              :         @par Exception Safety
     679              :         No-throw guarantee.
     680              : 
     681              :         @{
     682              :     */
     683              :     inline
     684              :     iterator
     685              :     end() noexcept;
     686              : 
     687              :     inline
     688              :     const_iterator
     689              :     end() const noexcept;
     690              :     /// @}
     691              : 
     692              :     /** Return a const iterator past the last element.
     693              : 
     694              :         The returned iterator only acts as a sentinel. Dereferencing it results
     695              :         in undefined behavior.
     696              : 
     697              :         @par Complexity
     698              :         Constant.
     699              : 
     700              :         @par Exception Safety
     701              :         No-throw guarantee.
     702              :     */
     703              :     inline
     704              :     const_iterator
     705              :     cend() const noexcept;
     706              : 
     707              :     /** Return a reverse iterator to the first element of the reversed container.
     708              : 
     709              :         The pointed-to element corresponds to the
     710              :         last element of the non-reversed container.
     711              :         If the container is empty, @ref rend() is returned.
     712              : 
     713              :         @par Complexity
     714              :         Constant.
     715              : 
     716              :         @par Exception Safety
     717              :         No-throw guarantee.
     718              : 
     719              :         @{
     720              :     */
     721              :     inline
     722              :     reverse_iterator
     723              :     rbegin() noexcept;
     724              : 
     725              :     inline
     726              :     const_reverse_iterator
     727              :     rbegin() const noexcept;
     728              :     /// @}
     729              : 
     730              :     /** Return a const reverse iterator to the first element of the reversed container.
     731              : 
     732              :         The pointed-to element corresponds to the
     733              :         last element of the non-reversed container.
     734              :         If the container is empty, @ref crend() is returned.
     735              : 
     736              :         @par Complexity
     737              :         Constant.
     738              : 
     739              :         @par Exception Safety
     740              :         No-throw guarantee.
     741              :     */
     742              :     inline
     743              :     const_reverse_iterator
     744              :     crbegin() const noexcept;
     745              : 
     746              :     /** Return a reverse iterator to the element following the last element of the reversed container.
     747              : 
     748              :         The pointed-to element corresponds to the element
     749              :         preceding the first element of the non-reversed container.
     750              :         The returned iterator only acts as a sentinel. Dereferencing it results
     751              :         in undefined behavior.
     752              : 
     753              :         @par Complexity
     754              :         Constant.
     755              : 
     756              :         @par Exception Safety
     757              :         No-throw guarantee.
     758              : 
     759              :         @{
     760              :     */
     761              :     inline
     762              :     reverse_iterator
     763              :     rend() noexcept;
     764              : 
     765              :     inline
     766              :     const_reverse_iterator
     767              :     rend() const noexcept;
     768              :     /// @}
     769              : 
     770              :     /** Return a const reverse iterator to the element following the last element of the reversed container.
     771              : 
     772              :         The pointed-to element corresponds to the element preceding the first
     773              :         element of the non-reversed container. The returned iterator only acts
     774              :         as a sentinel. Dereferencing it results in undefined behavior.
     775              : 
     776              :         @par Complexity
     777              :         Constant.
     778              : 
     779              :         @par Exception Safety
     780              :         No-throw guarantee.
     781              :     */
     782              :     inline
     783              :     const_reverse_iterator
     784              :     crend() const noexcept;
     785              : 
     786              :     //------------------------------------------------------
     787              :     //
     788              :     // Capacity
     789              :     //
     790              :     //------------------------------------------------------
     791              : 
     792              :     /** Return the number of elements in the array.
     793              : 
     794              :         This returns the number of elements in the array.
     795              :         The value returned may be different from the number
     796              :         returned from @ref capacity.
     797              : 
     798              :         @par Complexity
     799              :         Constant.
     800              : 
     801              :         @par Exception Safety
     802              :         No-throw guarantee.
     803              :     */
     804              :     inline
     805              :     std::size_t
     806              :     size() const noexcept;
     807              : 
     808              :     /** The maximum number of elements an array can hold.
     809              : 
     810              :         The maximum is an implementation-defined number. This value is
     811              :         a theoretical limit; at runtime, the actual maximum size may be less
     812              :         due to resource limits.
     813              : 
     814              :         @par Complexity
     815              :         Constant.
     816              : 
     817              :         @par Exception Safety
     818              :         No-throw guarantee.
     819              :     */
     820              :     static
     821              :     inline
     822              :     constexpr
     823              :     std::size_t
     824              :     max_size() noexcept;
     825              : 
     826              :     /** Return the number of elements that can be held in currently allocated memory.
     827              : 
     828              :         Returns the number of elements that the container has currently
     829              :         allocated space for. This number is never smaller than the value
     830              :         returned by @ref size().
     831              : 
     832              :         @par Complexity
     833              :         Constant.
     834              : 
     835              :         @par Exception Safety
     836              :         No-throw guarantee.
     837              :     */
     838              :     inline
     839              :     std::size_t
     840              :     capacity() const noexcept;
     841              : 
     842              :     /** Check if the array has no elements.
     843              : 
     844              :         Returns `true` if there are no elements in the
     845              :         array, i.e. @ref size() returns 0.
     846              : 
     847              :         @par Complexity
     848              :         Constant.
     849              : 
     850              :         @par Exception Safety
     851              :         No-throw guarantee.
     852              :     */
     853              :     inline
     854              :     bool
     855              :     empty() const noexcept;
     856              : 
     857              :     /** Increase the capacity to at least a certain amount.
     858              : 
     859              :         This increases the @ref capacity() to a value that is greater than or
     860              :         equal to `new_capacity`. If `new_capacity > capacity()`, new memory is
     861              :         allocated. Otherwise, the call has no effect. The number of elements
     862              :         and therefore the @ref size() of the container is not changed.
     863              : 
     864              :         If new memory is allocated, all iterators including any past-the-end
     865              :         iterators, and all references to the elements are invalidated.
     866              :         Otherwise, no iterators or references are invalidated.
     867              : 
     868              :         @par Complexity
     869              :         At most, linear in @ref size().
     870              : 
     871              :         @par Exception Safety
     872              :         Strong guarantee.
     873              :         Calls to `memory_resource::allocate` may throw.
     874              : 
     875              :         @param new_capacity The new capacity of the array.
     876              : 
     877              :         @throw boost::system::system_error `new_capacity >` @ref max_size().
     878              :     */
     879              :     inline
     880              :     void
     881              :     reserve(std::size_t new_capacity);
     882              : 
     883              :     /** Request the removal of unused capacity.
     884              : 
     885              :         This performs a non-binding request to reduce the
     886              :         capacity to the current size. The request may or
     887              :         may not be fulfilled. If reallocation occurs, all
     888              :         iterators including any past-the-end iterators,
     889              :         and all references to the elements are invalidated.
     890              :         Otherwise, no iterators or references are
     891              :         invalidated.
     892              : 
     893              :         @par Complexity
     894              :         At most, linear in @ref size().
     895              : 
     896              :         @par Exception Safety
     897              :         No-throw guarantee.
     898              :     */
     899              :     BOOST_JSON_DECL
     900              :     void
     901              :     shrink_to_fit() noexcept;
     902              : 
     903              :     //------------------------------------------------------
     904              :     //
     905              :     // Modifiers
     906              :     //
     907              :     //------------------------------------------------------
     908              : 
     909              :     /** Clear the contents.
     910              : 
     911              :         Erases all elements from the container. After this call, @ref size()
     912              :         returns zero but @ref capacity() is unchanged. All references,
     913              :         pointers, and iterators are invalidated
     914              : 
     915              :         @par Complexity
     916              :         Linear in @ref size().
     917              : 
     918              :         @par Exception Safety
     919              :         No-throw guarantee.
     920              :     */
     921              :     BOOST_JSON_DECL
     922              :     void
     923              :     clear() noexcept;
     924              : 
     925              :     /** Insert elements before the specified location.
     926              : 
     927              :         @li **(1)** and **(2)** insert a single new element before
     928              :             `pos`. **(1)** copy-constructs and **(2)** move-constructs the new
     929              :             element from `jv`.
     930              :         @li **(3)** inserts `count` copies of `jv` before `pos`.
     931              :         @li **(4)** the elements in the range `[first, last)` are inserted in
     932              :             order.
     933              :         @li **(5)** the elements of the initializer list `init` are inserted in
     934              :             order.
     935              : 
     936              :         Inserted values will be constructed using the container's
     937              :         associated @ref boost::container::pmr::memory_resource.
     938              : 
     939              :         @note Overload **(2)** is equivalent to **(1)** if
     940              :         `*jv.storage() != *this->storage()`.
     941              : 
     942              :         If the size of the array after insertion would have exceeded
     943              :         @ref capacity(), a reallocation occurs first, and all iterators and
     944              :         references are invalidated. Otherwise, only the iterators and
     945              :         references from the insertion point forward are invalidated. All
     946              :         past-the-end iterators are also invalidated.
     947              : 
     948              :         @pre
     949              :         `first` and `last` are not iterators into `*this`.
     950              : 
     951              :         @par Constraints
     952              :         @code
     953              :         ! std::is_convertible_v<InputIt, value>
     954              :         std::is_constructible_v<value, std::iterator_traits<InputIt>::reference>
     955              :         @endcode
     956              : 
     957              :         @par Complexity
     958              :         @li **(1)**, **(2)** linear in `std::distance(pos, end())`.
     959              :         @li **(3)** linear in `count + std::distance(pos, end())`.
     960              :         @li **(4)** linear in `std::distance(first, last) +
     961              :             std::distance(pos, end())`.
     962              :         @li **(5)** linear in `init.size() + std::distance(pos, end())`.
     963              : 
     964              :         @par Exception Safety
     965              :         {sp}**(4)** provides strong guarantee if `InputIt` satisfies
     966              :         {req_ForwardIterator}, and basic guarantee otherwise. Other overloads
     967              :         provide strong guarantee.
     968              :         Calls to `memory_resource::allocate` may throw.
     969              : 
     970              :         @param pos Iterator before which the new elements will
     971              :         be inserted. This may be the @ref end() iterator.
     972              : 
     973              :         @param jv The value to insert. A copy will be made
     974              :         using container's associated
     975              :         @ref boost::container::pmr::memory_resource.
     976              : 
     977              :         @return An iterator to the first inserted value, or `pos` if no values
     978              :                 were inserted.
     979              : 
     980              :         @{
     981              :     */
     982              :     BOOST_JSON_DECL
     983              :     iterator
     984              :     insert(
     985              :         const_iterator pos,
     986              :         value const& jv);
     987              : 
     988              :     // Overload
     989              :     BOOST_JSON_DECL
     990              :     iterator
     991              :     insert(
     992              :         const_iterator pos,
     993              :         value&& jv);
     994              : 
     995              : 
     996              :     /** Overload
     997              :         @param count The number of copies to insert.
     998              :         @param pos
     999              :         @param jv
    1000              :     */
    1001              :     BOOST_JSON_DECL
    1002              :     iterator
    1003              :     insert(
    1004              :         const_iterator pos,
    1005              :         std::size_t count,
    1006              :         value const& jv);
    1007              : 
    1008              :     /** Overload
    1009              : 
    1010              :         @param first An input iterator pointing to the first element to insert,
    1011              :                or pointing to the end of the range.
    1012              :         @param last An input iterator pointing to the end of the range.
    1013              :         @param pos
    1014              : 
    1015              :         @tparam InputIt a type satisfying the requirements
    1016              :         of {req_InputIterator}.
    1017              :     */
    1018              :     template<
    1019              :         class InputIt
    1020              :     #ifndef BOOST_JSON_DOCS
    1021              :         ,class = typename std::enable_if<
    1022              :             std::is_constructible<value,
    1023              :                 typename std::iterator_traits<
    1024              :                     InputIt>::reference>::value>::type
    1025              :     #endif
    1026              :     >
    1027              :     iterator
    1028              :     insert(
    1029              :         const_iterator pos,
    1030              :         InputIt first, InputIt last);
    1031              : 
    1032              :     /** Overload
    1033              :         @param init The initializer list to insert
    1034              :         @param pos
    1035              :     */
    1036              :     BOOST_JSON_DECL
    1037              :     iterator
    1038              :     insert(
    1039              :         const_iterator pos,
    1040              :         std::initializer_list<value_ref> init);
    1041              :     /// @}
    1042              : 
    1043              :     /** Insert a constructed element in-place.
    1044              : 
    1045              :         Inserts a new element into the container directly before
    1046              :         `pos`. The element is constructed using placement-new
    1047              :         with the parameter `std::forward<Arg>(arg)`.
    1048              :         If `capacity() < size() + 1`,
    1049              :         a reallocation occurs first, and all iterators and
    1050              :         references are invalidated.
    1051              :         Otherwise, only the iterators and references from
    1052              :         the insertion point forward are invalidated. All
    1053              :         past-the-end iterators are also invalidated.
    1054              : 
    1055              :         @par Complexity
    1056              :         Linear in `std::distance(pos, end())`.
    1057              : 
    1058              :         @par Exception Safety
    1059              :         Strong guarantee.
    1060              :         Calls to `memory_resource::allocate` may throw.
    1061              : 
    1062              :         @param pos Iterator before which the element will
    1063              :         be inserted. This may be the @ref end() iterator.
    1064              : 
    1065              :         @param arg The argument to forward to the @ref value
    1066              :         constructor.
    1067              : 
    1068              :         @return An iterator to the inserted element
    1069              :     */
    1070              :     template<class Arg>
    1071              :     iterator
    1072              :     emplace(
    1073              :         const_iterator pos,
    1074              :         Arg&& arg);
    1075              : 
    1076              :     /** Remove elements from the array.
    1077              : 
    1078              :         @li **(1)** the element at `pos` is removed.
    1079              :         @li **(2)** the elements in the range `[first, last)` are removed.
    1080              : 
    1081              :         @par Complexity
    1082              :         @li **(1)** linear in `std::distance(pos, end())`.
    1083              :         @li **(2)** linear in `std::distance(first, end())`.
    1084              : 
    1085              :         @par Exception Safety
    1086              :         No-throw guarantee.
    1087              : 
    1088              :         @param pos Iterator to the element to remove
    1089              : 
    1090              :         @return Iterator following the last removed element. If that was the
    1091              :                 last element of the array, the @ref end() iterator is returned.
    1092              : 
    1093              :         @{
    1094              :     */
    1095              :     BOOST_JSON_DECL
    1096              :     iterator
    1097              :     erase(const_iterator pos) noexcept;
    1098              : 
    1099              :     /** Overload
    1100              :         @param first An iterator pointing to the first element to erase, or
    1101              :                pointing to the end of the range.
    1102              :         @param last An iterator pointing to one past the last element to erase,
    1103              :                     or pointing to the end of the range.
    1104              :     */
    1105              :     BOOST_JSON_DECL
    1106              :     iterator
    1107              :     erase(
    1108              :         const_iterator first,
    1109              :         const_iterator last) noexcept;
    1110              :     /// @}
    1111              : 
    1112              :     /** Add an element to the end.
    1113              : 
    1114              :         Insert a new element at the end of the container. **(1)**
    1115              :         copy-constructs the new element from `jv`, **(2)** move-constructs from
    1116              :         `jv`.
    1117              : 
    1118              :         If `capacity() < size() + 1`, a reallocation occurs first, and all
    1119              :         iterators and references are invalidated. Any past-the-end iterators
    1120              :         are always invalidated.
    1121              : 
    1122              :         The new element will be constructed using the container's associated
    1123              :         @ref boost::container::pmr::memory_resource.
    1124              : 
    1125              :         @par Complexity
    1126              :         Amortized constant.
    1127              : 
    1128              :         @par Exception Safety
    1129              :         Strong guarantee.
    1130              :         Calls to `memory_resource::allocate` may throw.
    1131              : 
    1132              :         @param jv The value to insert.
    1133              : 
    1134              :         @{
    1135              :     */
    1136              :     BOOST_JSON_DECL
    1137              :     void
    1138              :     push_back(value const& jv);
    1139              : 
    1140              :     BOOST_JSON_DECL
    1141              :     void
    1142              :     push_back(value&& jv);
    1143              :     /// @}
    1144              : 
    1145              :     /** Append a constructed element in-place.
    1146              : 
    1147              :         Appends a new element to the end of the container's
    1148              :         list of elements.
    1149              :         The element is constructed using placement-new
    1150              :         with the parameter `std::forward<Arg>(arg)`.
    1151              :         If `capacity() < size() + 1`,
    1152              :         a reallocation occurs first, and all iterators and
    1153              :         references are invalidated.
    1154              :         Otherwise, only the iterators and references from
    1155              :         the insertion point forward are invalidated. All
    1156              :         past-the-end iterators are also invalidated.
    1157              : 
    1158              :         @par Complexity
    1159              :         Amortized constant.
    1160              : 
    1161              :         @par Exception Safety
    1162              :         Strong guarantee.
    1163              :         Calls to `memory_resource::allocate` may throw.
    1164              : 
    1165              :         @param arg The argument to forward to the @ref value
    1166              :         constructor.
    1167              : 
    1168              :         @return A reference to the inserted element
    1169              :     */
    1170              :     template<class Arg>
    1171              :     value&
    1172              :     emplace_back(Arg&& arg);
    1173              : 
    1174              :     /** Remove the last element
    1175              : 
    1176              :         The last element of the container is erased.
    1177              : 
    1178              :         @pre
    1179              :         `! empty()`
    1180              : 
    1181              :         @par Exception Safety
    1182              :         No-throw guarantee.
    1183              :     */
    1184              :     BOOST_JSON_DECL
    1185              :     void
    1186              :     pop_back() noexcept;
    1187              : 
    1188              :     /** Change the number of elements stored.
    1189              : 
    1190              :         Resizes the container to contain `count` elements.
    1191              : 
    1192              :         @li If `size() > count`, the container is reduced to its first `count`
    1193              :             elements.
    1194              :         @li If `size() < count`, additional null values (**(1)**) or copies
    1195              :             of `jv` (**(2)**) are appended.
    1196              : 
    1197              :         If `capacity() < count`, a reallocation occurs first, and all iterators
    1198              :         and references are invalidated. Any past-the-end iterators are always
    1199              :         invalidated.
    1200              : 
    1201              :         @par Complexity
    1202              :         Linear in `size() + count`.
    1203              : 
    1204              :         @par Exception Safety
    1205              :         Strong guarantee.
    1206              :         Calls to `memory_resource::allocate` may throw.
    1207              : 
    1208              :         @param count The new size of the container.
    1209              : 
    1210              :         @{
    1211              :     */
    1212              :     BOOST_JSON_DECL
    1213              :     void
    1214              :     resize(std::size_t count);
    1215              : 
    1216              :     /** Overload
    1217              :         @param jv The @ref value to copy into the new elements.
    1218              :         @param count
    1219              :     */
    1220              :     BOOST_JSON_DECL
    1221              :     void
    1222              :     resize(
    1223              :         std::size_t count,
    1224              :         value const& jv);
    1225              :     /// @}
    1226              : 
    1227              :     /** Swap two arrays.
    1228              : 
    1229              :         Exchanges the contents of this array with another array. Ownership of
    1230              :         the respective @ref boost::container::pmr::memory_resource objects is
    1231              :         not transferred. If `this == &other`, this function call has no effect.
    1232              : 
    1233              :         @li If `*storage() == *other.storage()` all iterators and references
    1234              :         remain valid.
    1235              : 
    1236              :         @li Otherwise, the contents are logically swapped by making copies,
    1237              :         which can throw. In this case all iterators and references are
    1238              :         invalidated.
    1239              : 
    1240              :         @par Complexity
    1241              :         If `*storage() == *other.storage()`, then constant; otherwise linear in
    1242              :         `size() + other.size()`.
    1243              : 
    1244              :         @par Exception Safety
    1245              :         No-throw guarantee if `*storage() == *other.storage()`. Otherwise
    1246              :         strong guarantee. Calls to `memory_resource::allocate` may throw.
    1247              : 
    1248              :         @param other The value to swap with.
    1249              :     */
    1250              :     BOOST_JSON_DECL
    1251              :     void
    1252              :     swap(array& other);
    1253              : 
    1254              :     /** Swap two arrays.
    1255              : 
    1256              :         Exchanges the contents of the array `lhs` with another array `rhs`.
    1257              :         Ownership of the respective @ref boost::container::pmr::memory_resource
    1258              :         objects is not transferred. If `&lhs == &rhs`, this function call has
    1259              :         no effect.
    1260              : 
    1261              :         @li If `*lhs.storage() == *rhs.storage()` all iterators and references
    1262              :         remain valid.
    1263              : 
    1264              :         @li Otherwise, the contents are logically swapped by making copies,
    1265              :         which can throw. In this case all iterators and references are
    1266              :         invalidated.
    1267              : 
    1268              :         @par Complexity
    1269              :         If `*lhs.storage() == *rhs.storage()`, then constant; otherwise linear
    1270              :         in `lhs.size() + rhs.size()`.
    1271              : 
    1272              :         @par Exception Safety
    1273              :         No-throw guarantee if `*lhs.storage() == *rhs.storage()`. Otherwise
    1274              :         strong guarantee. Calls to `memory_resource::allocate` may throw.
    1275              : 
    1276              :         @param lhs The array to exchange.
    1277              : 
    1278              :         @param rhs The array to exchange.
    1279              :         If `&lhs == &rhs`, this function call has no effect.
    1280              : 
    1281              :         @see @ref array::swap
    1282              :     */
    1283              :     friend
    1284              :     void
    1285            1 :     swap(array& lhs, array& rhs)
    1286              :     {
    1287            1 :         lhs.swap(rhs);
    1288            1 :     }
    1289              : 
    1290              :     /** Compare two arrays for equality.
    1291              : 
    1292              :         Arrays are equal when their sizes are the same, and they are
    1293              :         element-for-element equal in order.
    1294              : 
    1295              :         @par Complexity
    1296              :         Linear in `lhs.size()`.
    1297              : 
    1298              :         @par Exception Safety
    1299              :         No-throw guarantee.
    1300              :     */
    1301              :     // inline friend speeds up overload resolution
    1302              :     friend
    1303              :     bool
    1304           96 :     operator==(
    1305              :         array const& lhs,
    1306              :         array const& rhs) noexcept
    1307              :     {
    1308           96 :         return lhs.equal(rhs);
    1309              :     }
    1310              : 
    1311              :     /** Compare two arrays for inequality.
    1312              : 
    1313              :         Arrays are equal when their sizes are the same, and they are
    1314              :         element-for-element equal in order.
    1315              : 
    1316              :         @par Complexity
    1317              :         Linear in `lhs.size()`.
    1318              : 
    1319              :         @par Exception Safety
    1320              :         No-throw guarantee.
    1321              :     */
    1322              :     // inline friend speeds up overload resolution
    1323              :     friend
    1324              :     bool
    1325            9 :     operator!=(
    1326              :         array const& lhs,
    1327              :         array const& rhs) noexcept
    1328              :     {
    1329            9 :         return ! (lhs == rhs);
    1330              :     }
    1331              : 
    1332              :     /** Serialize to an output stream.
    1333              : 
    1334              :         This function serializes an `array` as JSON into the output stream.
    1335              : 
    1336              :         @return Reference to `os`.
    1337              : 
    1338              :         @par Complexity
    1339              :         Constant or linear in the size of `arr`.
    1340              : 
    1341              :         @par Exception Safety
    1342              :         Strong guarantee.
    1343              :         Calls to `memory_resource::allocate` may throw.
    1344              : 
    1345              :         @param os The output stream to serialize to.
    1346              : 
    1347              :         @param arr The value to serialize.
    1348              :     */
    1349              :     BOOST_JSON_DECL
    1350              :     friend
    1351              :     std::ostream&
    1352              :     operator<<(
    1353              :         std::ostream& os,
    1354              :         array const& arr);
    1355              : 
    1356              : private:
    1357              :     template<class It>
    1358              :     using iter_cat = typename
    1359              :         std::iterator_traits<It>::iterator_category;
    1360              : 
    1361              :     template<class InputIt>
    1362              :     array(
    1363              :         InputIt first, InputIt last,
    1364              :         storage_ptr sp,
    1365              :         std::input_iterator_tag);
    1366              : 
    1367              :     template<class InputIt>
    1368              :     array(
    1369              :         InputIt first, InputIt last,
    1370              :         storage_ptr sp,
    1371              :         std::forward_iterator_tag);
    1372              : 
    1373              :     inline
    1374              :     std::size_t
    1375              :     growth(std::size_t new_size) const;
    1376              : 
    1377              :     BOOST_JSON_DECL
    1378              :     void
    1379              :     reserve_impl(
    1380              :         std::size_t new_capacity);
    1381              : 
    1382              :     BOOST_JSON_DECL
    1383              :     value&
    1384              :     push_back(
    1385              :         pilfered<value> pv);
    1386              : 
    1387              :     BOOST_JSON_DECL
    1388              :     iterator
    1389              :     insert(
    1390              :         const_iterator pos,
    1391              :         pilfered<value> pv);
    1392              : 
    1393              :     template<class InputIt>
    1394              :     iterator
    1395              :     insert(
    1396              :         const_iterator pos,
    1397              :         InputIt first, InputIt last,
    1398              :         std::input_iterator_tag);
    1399              : 
    1400              :     template<class InputIt>
    1401              :     iterator
    1402              :     insert(
    1403              :         const_iterator pos,
    1404              :         InputIt first, InputIt last,
    1405              :         std::forward_iterator_tag);
    1406              : 
    1407              :     BOOST_JSON_DECL
    1408              :     bool
    1409              :     equal(array const& other) const noexcept;
    1410              : };
    1411              : 
    1412              : } // namespace json
    1413              : } // namespace boost
    1414              : 
    1415              : // std::hash specialization
    1416              : #ifndef BOOST_JSON_DOCS
    1417              : namespace std {
    1418              : template <>
    1419              : struct hash< ::boost::json::array > {
    1420              :     BOOST_JSON_DECL
    1421              :     std::size_t
    1422              :     operator()(::boost::json::array const& ja) const noexcept;
    1423              : };
    1424              : } // std
    1425              : #endif
    1426              : 
    1427              : // Must be included here for this file to stand alone
    1428              : #include <boost/json/value.hpp>
    1429              : 
    1430              : // includes are at the bottom of <boost/json/value.hpp>
    1431              : 
    1432              : #endif
        

Generated by: LCOV version 2.1