19#include <daw/daw_arith_traits.h>
20#include <daw/daw_enable_requires.h>
21#include <daw/daw_move.h>
22#include <daw/daw_string_view.h>
31 namespace json_details {
33 typename Allocator = NoAllocator>
34 class basic_stateful_json_value_state {
39 daw::string_view name;
42 explicit constexpr basic_stateful_json_value_state(
43 daw::string_view Name,
46 , location( std::move( val ) ) {}
48 [[nodiscard]]
constexpr bool is_match( daw::string_view Name )
const {
49 return names_equal( name, Name );
58 : name(
std::data( Name ),
std::size( Name ) ) {}
66 template<
json_options_t PolicyFlags = json_details::default_policy_flag,
67 typename Allocator = json_details::NoAllocator>
74 json_details::basic_stateful_json_value_state<PolicyFlags, Allocator>>
84 std::size_t
const Sz = std::size( m_locs );
85 for( ; pos < Sz; ++pos ) {
86 if( m_locs[pos].is_match( member.
name ) ) {
92 if( m_locs.empty( ) ) {
93 return m_value.
begin( );
95 auto res = m_locs.back( ).location;
99 auto const last = m_value.
end( );
100 while( it != last ) {
101 auto name = it.
name( );
103 auto const &new_loc = m_locs.emplace_back(
104 daw::string_view( std::data( *name ), std::size( *name ) ), it );
105 if( new_loc.is_match( member.
name ) ) {
111 return std::size( m_locs );
119 [[nodiscard]]
constexpr std::size_t
move_to( std::size_t index ) {
120 if( index < std::size( m_locs ) ) {
124 if( m_locs.empty( ) ) {
125 return m_value.
begin( );
127 auto res = m_locs.back( ).location;
131 auto last = m_value.
end( );
132 std::size_t pos = std::size( m_locs );
133 while( it != last ) {
134 auto name = it.name( );
137 daw::string_view( std::data( *name ), std::size( *name ) ), it );
139 m_locs.emplace_back( daw::string_view( ), it );
147 return std::size( m_locs );
153 : m_value(
std::move( val ) ) {
156 auto t = m_value.
type( );
157 return ( t == JsonBaseParseTypes::Class ) |
158 ( t == JsonBaseParseTypes::Array );
160 ErrorReason::ExpectedArrayOrClassStart,
177 m_value = std::move( val );
190 ErrorReason::UnknownMember );
191 return m_locs[pos].location->value;
201 std::size_t pos = move_to( member );
203 ErrorReason::UnknownMember );
204 return m_locs[pos].location->value;
213 at( std::string_view key ) {
214 auto const k = std::string_view( std::data( key ), std::size( key ) );
215 std::size_t pos = move_to( k );
216 if( pos < std::size( m_locs ) ) {
217 return m_locs[pos].location->value;
227 [[nodiscard]] std::size_t
size( ) {
229 switch( current_type ) {
230 case JsonBaseParseTypes::Array:
231 case JsonBaseParseTypes::Class:
232 return move_to( daw::max_value<std::size_t> );
233 case JsonBaseParseTypes::Number:
234 case JsonBaseParseTypes::Bool:
235 case JsonBaseParseTypes::String:
236 case JsonBaseParseTypes::Null:
237 case JsonBaseParseTypes::None:
249 [[nodiscard]] std::size_t
index_of( std::string_view key ) {
259 [[nodiscard]]
constexpr bool contains( std::string_view key ) {
260 auto const k = std::string_view( std::data( key ), std::size( key ) );
261 return move_to( k ) < std::size( m_locs );
270 [[nodiscard]]
constexpr bool contains( std::size_t index ) {
271 return move_to( index ) < size( m_locs );
281 template<
typename Integer>
282 [[nodiscard]] std::optional<std::string_view>
name_of( Integer index ) {
283 static_assert( std::is_integral_v<Integer>,
284 "Only integer indices are allowed" );
285 if constexpr( std::is_signed_v<Integer> ) {
289 if(
static_cast<std::size_t
>( index ) >= sz ) {
292 sz -=
static_cast<std::size_t
>( index );
293 return std::string_view( std::data( m_locs[sz].name( ) ),
294 std::size( m_locs[sz].name( ) ) );
297 std::size_t pos = move_to(
static_cast<std::size_t
>( index ) );
298 if( pos < std::size( m_locs ) ) {
299 return std::string_view( std::data( m_locs[pos].name( ) ),
300 std::size( m_locs[pos].name( ) ) );
313 template<
typename Integer DAW_ENABLEIF( std::is_
integral_v<Integer> )>
317 if constexpr( std::is_signed_v<Integer> ) {
322 ErrorReason::UnknownMember );
323 sz -=
static_cast<std::size_t
>( index );
324 return m_locs[sz].location->value;
327 std::size_t pos = move_to(
static_cast<std::size_t
>( index ) );
329 ErrorReason::UnknownMember );
330 return m_locs[pos].location->value;
340 template<
typename Integer DAW_ENABLEIF( std::is_
integral_v<Integer> )>
342 [[nodiscard]]
constexpr std::optional<
344 if constexpr( std::is_signed_v<Integer> ) {
348 if(
static_cast<std::size_t
>( index ) >= sz ) {
351 sz -=
static_cast<std::size_t
>( index );
352 return m_locs[sz].location->value( );
355 std::size_t pos = move_to(
static_cast<std::size_t
>( index ) );
356 if( pos < std::size( m_locs ) ) {
357 return m_locs[pos].location->value( );
373 template<json_options_t PolicyFlags,
typename Allocator>
constexpr bool contains(std::string_view key)
Is the named member present. This method is O(N) worst case and O(1) if the locations have already.
constexpr basic_json_value< PolicyFlags, Allocator > at(std::string_view key)
Create a basic_json_member for the named member.
std::size_t index_of(std::string_view key)
Return the index of named member. This method is O(N) worst case and O(1) if the locations have alrea...
constexpr std::size_t move_to(std::size_t index)
constexpr basic_json_value< PolicyFlags, Allocator > get_json_value() const
constexpr std::size_t move_to(json_member_name member)
basic_json_value< PolicyFlags, Allocator > m_value
constexpr basic_json_value< PolicyFlags, Allocator > operator[](Integer index)
std::optional< std::string_view > name_of(Integer index)
constexpr basic_stateful_json_value()
constexpr basic_stateful_json_value(daw::string_view json_data)
std::size_t size()
Count the number of elements/members in the JSON class or array This method is O(N) worst case and O(...
constexpr std::optional< basic_json_value< PolicyFlags, Allocator > > at(Integer index)
constexpr basic_json_value< PolicyFlags, Allocator > operator[](json_member_name member)
Create a basic_json_member for the named member.
TryDefaultParsePolicy< BasicParsePolicy< PolicyFlags, Allocator > > ParseState
constexpr basic_stateful_json_value(basic_json_value< PolicyFlags, Allocator > val)
constexpr bool contains(std::size_t index)
constexpr basic_json_value< PolicyFlags, Allocator > operator[](std::string_view key)
Create a basic_json_member for the named member.
constexpr void reset(basic_json_value< PolicyFlags, Allocator > val)
#define daw_json_assert_weak(Bool,...)
Assert that Bool is true when in Checked Input mode If false pass rest of args to daw_json_error.
DAW_REQUIRES(daw::json::json_details::is_container_opted_into_json_iostreams_v< Container >) std
An opt in ostream interface for containers of types that have JSON mappings.
JsonBaseParseTypes
The fundamental JSON types.
std::uint32_t json_options_t
daw::conditional_t< ParsePolicy::is_default_parse_policy, DefaultParsePolicy, ParsePolicy > TryDefaultParsePolicy
string_writer grows its string with resize_and_overwrite, leaving the new bytes uninitialized,...
Iterator for iterating over arbitrary JSON members and array elements.
constexpr std::optional< std::string_view > name() const
Name of member.
A non-owning container for arbitrary JSON values that allows movement/iteration through.
constexpr iterator end() const
End of range over class/arrays members/items.
constexpr iterator begin() const
Get the first member/item.
constexpr ParseState get_raw_state() const
Get a copy of the underlying parse state.
constexpr JsonBaseParseTypes type() const
Get the type of JSON value.
constexpr json_member_name(std::string_view Name)
#define DAW_JSON_VER
The version string used in namespace definitions. Must be a valid namespace name.