DAW JSON Link
daw_json_parse_kv_array_iterator.h
Go to the documentation of this file.
1 // Copyright( c ) Darrell Wright
2 //
3 // Distributed under the Boost Software License, Version 1.0. (See accompanying
4 // file LICENSE or copy at http://www.boost.org/LICENSE_1_0.txt)
5 //
6 // Official repository: https://github.com/beached/daw_json_link
7 //
8 
9 #pragma once
10 
11 #include "daw_json_arrow_proxy.h"
12 #include "daw_json_assert.h"
14 #include "version.h"
15 
16 #include <daw/daw_attributes.h>
17 #include <daw/daw_move.h>
18 
19 #include <ciso646>
20 
21 namespace daw::json {
22  inline namespace DAW_JSON_VER {
23  namespace json_details {
24  template<typename ParseState, bool>
26  using iterator_category = std::input_iterator_tag;
27  using difference_type = std::ptrdiff_t;
28  static constexpr bool has_counter = false;
29  ParseState *parse_state = nullptr;
30  };
31 
32  template<typename ParseState>
33  struct json_parse_kv_array_iterator_base<ParseState, true> {
34  // We have to lie so that std::distance uses O(1) instead of O(N)
35  using iterator_category = std::random_access_iterator_tag;
36  using difference_type = std::ptrdiff_t;
37  static constexpr bool has_counter = true;
38  ParseState *parse_state = nullptr;
39  difference_type counter = 0;
40 
41  constexpr json_parse_kv_array_iterator_base( ) = default;
42 
43  explicit inline constexpr json_parse_kv_array_iterator_base(
44  ParseState *pd ) noexcept
45  : parse_state( pd )
46  , counter( static_cast<difference_type>( pd->counter ) ) {}
47 
48  inline constexpr difference_type
50  // rhs is the iterator with the parser in it. We should know how many
51  // items are in play because we already counted them in the skip_array
52  // call.
53  return rhs.counter;
54  }
55  };
56 
57  template<typename JsonMember, typename ParseState, bool KnownBounds>
60  can_random_v<KnownBounds>> {
61 
62  using base =
64  can_random_v<KnownBounds>>;
66  using json_key_t = typename JsonMember::json_key_t;
67  using json_element_t = typename JsonMember::json_value_t;
68  using value_type = std::pair<typename json_key_t::parse_to_t const,
69  typename json_element_t::parse_to_t>;
72  using parse_state_t = ParseState;
74 
75  using json_class_type = typename JsonMember::json_class_t;
76  inline constexpr json_parse_kv_array_iterator( ) = default;
77 
78  inline constexpr explicit json_parse_kv_array_iterator(
79  parse_state_t &r )
80  : base{ &r } {
81  if( DAW_UNLIKELY( base::parse_state->front( ) == ']' ) ) {
82  if constexpr( not KnownBounds ) {
83  // Cleanup at end of value
84  base::parse_state->remove_prefix( );
85  base::parse_state->trim_left_checked( );
86  // Ensure we are equal to default
87  }
88  base::parse_state = nullptr;
89  }
90  }
91 
92  static inline constexpr value_type
93  get_pair( typename json_class_type::parse_to_t &&v ) {
94  return value_type( std::get<0>( DAW_MOVE( v.members ) ),
95  std::get<1>( DAW_MOVE( v.members ) ) );
96  }
97 
98  DAW_ATTRIB_INLINE inline constexpr value_type operator*( ) {
100  base::parse_state and base::parse_state->has_more( ),
101  ErrorReason::UnexpectedEndOfData, *base::parse_state );
102 
103  return get_pair( parse_value<json_class_type>(
105  }
106 
107  DAW_ATTRIB_INLINE inline constexpr json_parse_kv_array_iterator &
110  ErrorReason::UnexpectedEndOfData );
111  base::parse_state->trim_left( );
112 
114  base::parse_state->has_more( ) and
115  base::parse_state->is_at_next_array_element( ),
116  ErrorReason::UnexpectedEndOfData, *base::parse_state );
117 
118  base::parse_state->move_next_member_or_end( );
120  ErrorReason::UnexpectedEndOfData );
121  if( DAW_UNLIKELY( base::parse_state->front( ) == ']' ) ) {
122 #ifndef NDEBUG
123  if constexpr( base::has_counter ) {
124  daw_json_assert_weak( base::counter == 0,
125  ErrorReason::UnexpectedEndOfData );
126  }
127 #endif
128  if constexpr( not KnownBounds ) {
129  // Cleanup at end of value
130  base::parse_state->remove_prefix( );
131  base::parse_state->trim_left_checked( );
132  // Ensure we are equal to default
133  }
134  base::parse_state = nullptr;
135  }
136 #ifndef NDEBUG
137  if constexpr( base::has_counter ) {
138  daw_json_assert_weak( base::counter > 0,
139  ErrorReason::UnexpectedEndOfData );
140  --base::counter;
141  }
142 #endif
143  return *this;
144  }
145 
146  friend inline constexpr bool
148  json_parse_kv_array_iterator const &rhs ) {
149  return lhs.parse_state == rhs.parse_state;
150  }
151 
152  friend inline constexpr bool
154  json_parse_kv_array_iterator const &rhs ) {
155  return not( lhs == rhs );
156  }
157  };
158  } // namespace json_details
159  } // namespace DAW_JSON_VER
160 } // namespace daw::json
#define daw_json_assert_weak(Bool,...)
Definition: daw_json_assert.h:189
std::integral_constant< JsonParseTypes, v > ParseTag
Definition: daw_json_enums.h:106
Definition: daw_from_json.h:22
Definition: daw_json_arrow_proxy.h:16
constexpr difference_type operator-(json_parse_kv_array_iterator_base const &rhs) const
Definition: daw_json_parse_kv_array_iterator.h:49
std::ptrdiff_t difference_type
Definition: daw_json_parse_kv_array_iterator.h:36
std::random_access_iterator_tag iterator_category
Definition: daw_json_parse_kv_array_iterator.h:35
constexpr json_parse_kv_array_iterator_base(ParseState *pd) noexcept
Definition: daw_json_parse_kv_array_iterator.h:43
Definition: daw_json_parse_kv_array_iterator.h:25
std::ptrdiff_t difference_type
Definition: daw_json_parse_kv_array_iterator.h:27
ParseState * parse_state
Definition: daw_json_parse_kv_array_iterator.h:29
static constexpr bool has_counter
Definition: daw_json_parse_kv_array_iterator.h:28
std::input_iterator_tag iterator_category
Definition: daw_json_parse_kv_array_iterator.h:26
Definition: daw_json_parse_kv_array_iterator.h:60
constexpr json_parse_kv_array_iterator(parse_state_t &r)
Definition: daw_json_parse_kv_array_iterator.h:78
ParseState parse_state_t
Definition: daw_json_parse_kv_array_iterator.h:72
value_type reference
Definition: daw_json_parse_kv_array_iterator.h:70
static constexpr value_type get_pair(typename json_class_type::parse_to_t &&v)
Definition: daw_json_parse_kv_array_iterator.h:93
constexpr DAW_ATTRIB_INLINE json_parse_kv_array_iterator & operator++()
Definition: daw_json_parse_kv_array_iterator.h:108
constexpr friend bool operator==(json_parse_kv_array_iterator const &lhs, json_parse_kv_array_iterator const &rhs)
Definition: daw_json_parse_kv_array_iterator.h:147
typename base::difference_type difference_type
Definition: daw_json_parse_kv_array_iterator.h:73
typename base::iterator_category iterator_category
Definition: daw_json_parse_kv_array_iterator.h:65
constexpr friend bool operator!=(json_parse_kv_array_iterator const &lhs, json_parse_kv_array_iterator const &rhs)
Definition: daw_json_parse_kv_array_iterator.h:153
std::pair< typename json_key_t::parse_to_t const, typename json_element_t::parse_to_t > value_type
Definition: daw_json_parse_kv_array_iterator.h:69
constexpr DAW_ATTRIB_INLINE value_type operator*()
Definition: daw_json_parse_kv_array_iterator.h:98
typename JsonMember::json_class_t json_class_type
Definition: daw_json_parse_kv_array_iterator.h:75
typename JsonMember::json_key_t json_key_t
Definition: daw_json_parse_kv_array_iterator.h:66
typename JsonMember::json_value_t json_element_t
Definition: daw_json_parse_kv_array_iterator.h:67
#define DAW_JSON_VER
Definition: version.h:11