Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
J
json
Project
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Chen Yisong
json
Commits
6ef1614f
Commit
6ef1614f
authored
Jan 12, 2021
by
Anthony VH
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Refactor json::get() to use priority_tag.
parent
6278f31d
Hide whitespace changes
Inline
Side-by-side
Showing
1 changed file
with
169 additions
and
143 deletions
+169
-143
json.hpp
include/nlohmann/json.hpp
+169
-143
No files found.
include/nlohmann/json.hpp
View file @
6ef1614f
...
...
@@ -2838,50 +2838,53 @@ class basic_json
/// @{
/*!
@brief get
special-case overload
@brief get
a pointer value (implicit)
This overloads avoids a lot of template boilerplate, it can be seen as th
e
identity method
Implicit pointer access to the internally stored JSON value. No copies ar
e
made.
@tparam BasicJsonType == @ref basic_json
@warning Writing data to the pointee of the result yields an undefined
state.
@return a copy of *this
@tparam PointerType pointer type; must be a pointer to @ref array_t, @ref
object_t, @ref string_t, @ref boolean_t, @ref number_integer_t,
@ref number_unsigned_t, or @ref number_float_t. Enforced by a static
assertion.
@return pointer to the internally stored JSON value if the requested
pointer type @a PointerType fits to the JSON value; `nullptr` otherwise
@complexity Constant.
@since version 2.1.0
@liveexample{The example below shows how pointers to internal values of a
JSON value can be requested. Note that no type conversions are made and a
`nullptr` is returned if the value and the requested pointer type does not
match.,get_ptr}
@since version 1.0.0
*/
template
<
typename
BasicJsonType
,
detail
::
enable_if_t
<
std
::
is_same
<
typename
std
::
remove_const
<
BasicJsonType
>::
type
,
basic_json_t
>::
value
,
int
>
=
0
>
basic_json
get
()
const
template
<
typename
PointerType
,
typename
std
::
enable_if
<
std
::
is_pointer
<
PointerType
>::
value
,
int
>::
type
=
0
>
auto
get_ptr
()
noexcept
->
decltype
(
std
::
declval
<
basic_json_t
&>
().
get_impl_ptr
(
std
::
declval
<
PointerType
>
()))
{
return
*
this
;
// delegate the call to get_impl_ptr<>()
return
get_impl_ptr
(
static_cast
<
PointerType
>
(
nullptr
));
}
/*!
@brief get special-case overload
This overloads converts the current @ref basic_json in a different
@ref basic_json type
@tparam BasicJsonType == @ref basic_json
@return a copy of *this, converted into @tparam BasicJsonType
@complexity Depending on the implementation of the called `from_json()`
method.
@since version 3.2.0
@brief get a pointer value (implicit)
@copydoc get_ptr()
*/
template
<
typename
BasicJsonType
,
detail
::
enable_if_t
<
!
std
::
is_same
<
BasicJsonType
,
basic_json
>::
value
&&
detail
::
is_basic_json
<
BasicJsonType
>::
value
,
int
>
=
0
>
BasicJsonType
get
()
const
template
<
typename
PointerType
,
typename
std
::
enable_if
<
std
::
is_pointer
<
PointerType
>::
value
&&
std
::
is_const
<
typename
std
::
remove_pointer
<
PointerType
>::
type
>::
value
,
int
>::
type
=
0
>
constexpr
auto
get_ptr
()
const
noexcept
->
decltype
(
std
::
declval
<
const
basic_json_t
&>
().
get_impl_ptr
(
std
::
declval
<
PointerType
>
()))
{
return
*
this
;
// delegate the call to get_impl_ptr<>() const
return
get_impl_ptr
(
static_cast
<
PointerType
>
(
nullptr
));
}
private
:
/*!
@brief get a value (explicit)
...
...
@@ -2923,21 +2926,12 @@ class basic_json
*/
template
<
typename
ValueTypeCV
,
typename
ValueType
=
detail
::
uncvref_t
<
ValueTypeCV
>
,
detail
::
enable_if_t
<
!
detail
::
is_basic_json
<
ValueType
>::
value
&&
detail
::
has_from_json
<
basic_json_t
,
ValueType
>::
value
&&
!
detail
::
has_non_default_from_json
<
basic_json_t
,
ValueType
>::
value
,
detail
::
is_default_constructible
<
ValueType
>::
value
&&
detail
::
has_from_json
<
basic_json_t
,
ValueType
>::
value
,
int
>
=
0
>
ValueType
get
(
)
const
noexcept
(
noexcept
(
JSONSerializer
<
ValueType
>::
from_json
(
std
::
declval
<
const
basic_json_t
&>
(),
std
::
declval
<
ValueType
&>
())))
ValueType
get
_impl
(
detail
::
priority_tag
<
0
>
/*unused*/
)
const
noexcept
(
noexcept
(
JSONSerializer
<
ValueType
>::
from_json
(
std
::
declval
<
const
basic_json_t
&>
(),
std
::
declval
<
ValueType
&>
())))
{
// we cannot static_assert on ValueTypeCV being non-const, because
// there is support for get<const basic_json_t>(), which is why we
// still need the uncvref
static_assert
(
!
std
::
is_reference
<
ValueTypeCV
>::
value
,
"get() cannot be used with reference types, you might want to use get_ref()"
);
static_assert
(
std
::
is_default_constructible
<
ValueType
>::
value
,
"types must be DefaultConstructible when used with get()"
);
ValueType
ret
;
JSONSerializer
<
ValueType
>::
from_json
(
*
this
,
ret
);
return
ret
;
...
...
@@ -2975,133 +2969,107 @@ class basic_json
@since version 2.1.0
*/
template
<
typename
ValueTypeCV
,
typename
ValueType
=
detail
::
uncvref_t
<
ValueTypeCV
>
,
detail
::
enable_if_t
<
!
std
::
is_same
<
basic_json_t
,
ValueType
>::
value
&&
detail
::
has_non_default_from_json
<
basic_json_t
,
ValueType
>::
value
,
int
>
=
0
>
ValueType
get
(
)
const
noexcept
(
noexcept
(
JSONSerializer
<
ValueType
>::
from_json
(
std
::
declval
<
const
basic_json_t
&>
())))
detail
::
enable_if_t
<
detail
::
has_non_default_from_json
<
basic_json_t
,
ValueType
>::
value
,
int
>
=
0
>
ValueType
get
_impl
(
detail
::
priority_tag
<
1
>
/*unused*/
)
const
noexcept
(
noexcept
(
JSONSerializer
<
ValueType
>::
from_json
(
std
::
declval
<
const
basic_json_t
&>
())))
{
static_assert
(
!
std
::
is_reference
<
ValueTypeCV
>::
value
,
"get() cannot be used with reference types, you might want to use get_ref()"
);
return
JSONSerializer
<
ValueType
>::
from_json
(
*
this
);
}
/*!
@brief get a value (explicit)
Explicit type conversion between the JSON value and a compatible value.
The value is filled into the input parameter by calling the @ref json_serializer<ValueType>
`from_json()` method.
The function is equivalent to executing
@code {.cpp}
ValueType v;
JSONSerializer<ValueType>::from_json(*this, v);
@endcode
This overloads is chosen if:
- @a ValueType is not @ref basic_json,
- @ref json_serializer<ValueType> has a `from_json()` method of the form
`void from_json(const basic_json&, ValueType&)`, and
@brief get special-case overload
@tparam ValueType the input parameter type.
This overloads converts the current @ref basic_json in a different
@ref basic_json type
@
return the input parameter, allowing chaining calls.
@
tparam BasicJsonType == @ref basic_json
@
throw what @ref json_serializer<ValueType> `from_json()` method throws
@
return a copy of *this, converted into @tparam BasicJsonType
@liveexample{The example below shows several conversions from JSON values
to other types. There a few things to note: (1) Floating-point numbers can
be converted to integers\, (2) A JSON array can be converted to a standard
`std::vector<short>`\, (3) A JSON object can be converted to C++
associative containers such as `std::unordered_map<std::string\,
json>`.,get_to}
@complexity Depending on the implementation of the called `from_json()`
method.
@since version 3.
3
.0
@since version 3.
2
.0
*/
template
<
typename
ValueType
,
detail
::
enable_if_t
<
!
detail
::
is_basic_json
<
ValueType
>::
value
&&
detail
::
has_from_json
<
basic_json_t
,
ValueType
>::
value
,
template
<
typename
BasicJsonType
,
detail
::
enable_if_t
<
detail
::
is_basic_json
<
BasicJsonType
>::
value
,
int
>
=
0
>
ValueType
&
get_to
(
ValueType
&
v
)
const
noexcept
(
noexcept
(
JSONSerializer
<
ValueType
>::
from_json
(
std
::
declval
<
const
basic_json_t
&>
(),
v
)))
BasicJsonType
get_impl
(
detail
::
priority_tag
<
2
>
/*unused*/
)
const
{
JSONSerializer
<
ValueType
>::
from_json
(
*
this
,
v
);
return
v
;
return
*
this
;
}
// specialization to allow to call get_to with a basic_json value
// see https://github.com/nlohmann/json/issues/2175
template
<
typename
ValueType
,
detail
::
enable_if_t
<
detail
::
is_basic_json
<
ValueType
>::
value
,
/*!
@brief get special-case overload
This overloads avoids a lot of template boilerplate, it can be seen as the
identity method
@tparam BasicJsonType == @ref basic_json
@return a copy of *this
@complexity Constant.
@since version 2.1.0
*/
template
<
typename
BasicJsonType
,
detail
::
enable_if_t
<
std
::
is_same
<
BasicJsonType
,
basic_json_t
>::
value
,
int
>
=
0
>
ValueType
&
get_to
(
ValueType
&
v
)
const
basic_json
get_impl
(
detail
::
priority_tag
<
3
>
/*unused*/
)
const
{
v
=
*
this
;
return
v
;
return
*
this
;
}
template
<
typename
T
,
std
::
size_t
N
,
typename
Array
=
T
(
&
)[
N
],
detail
::
enable_if_t
<
detail
::
has_from_json
<
basic_json_t
,
Array
>::
value
,
int
>
=
0
>
Array
get_to
(
T
(
&
v
)[
N
])
const
noexcept
(
noexcept
(
JSONSerializer
<
Array
>::
from_json
(
std
::
declval
<
const
basic_json_t
&>
(),
v
)
))
/*!
@brief get a pointer value (explicit)
@copydoc get()
*/
template
<
typename
PointerType
,
detail
::
enable_if_t
<
std
::
is_pointer
<
PointerType
>::
value
,
int
>
=
0
>
constexpr
auto
get_impl
(
detail
::
priority_tag
<
4
>
/*unused*/
)
const
noexcept
->
decltype
(
std
::
declval
<
const
basic_json_t
&>
().
template
get_ptr
<
PointerType
>
(
))
{
JSONSerializer
<
Array
>::
from_json
(
*
this
,
v
);
return
v
;
// delegate the call to get_ptr
return
get_ptr
<
PointerType
>
()
;
}
public
:
/*!
@brief get a
pointer value (im
plicit)
@brief get a
(pointer) value (ex
plicit)
Implicit pointer access to the internally stored JSON value. No copies are
made.
Performs explicit type conversion between the JSON value and a compatible value if required.
@warning Writing data to the pointee of the result yields an undefined
stat
e.
- If the requested type is a pointer to the internally stored JSON value that pointer is returned.
No copies are mad
e.
@tparam PointerType pointer type; must be a pointer to @ref array_t, @ref
object_t, @ref string_t, @ref boolean_t, @ref number_integer_t,
@ref number_unsigned_t, or @ref number_float_t. Enforced by a static
assertion.
- If the requested type is the current @ref basic_json, or a different @ref basic_json convertible
from the current @ref basic_json.
@return pointer to the internally stored JSON value if the requested
pointer type @a PointerType fits to the JSON value; `nullptr` otherwise
- Otherwise the value is converted by calling the @ref json_serializer<ValueType> `from_json()`
method.
@complexity Constant.
@tparam ValueTypeCV the provided value type
@tparam ValueType the returned value type
@liveexample{The example below shows how pointers to internal values of a
JSON value can be requested. Note that no type conversions are made and a
`nullptr` is returned if the value and the requested pointer type does not
match.,get_ptr}
@return copy of the JSON value, converted to @tparam ValueType if necessary
@since version 1.0.0
*/
template
<
typename
PointerType
,
typename
std
::
enable_if
<
std
::
is_pointer
<
PointerType
>::
value
,
int
>::
type
=
0
>
auto
get_ptr
()
noexcept
->
decltype
(
std
::
declval
<
basic_json_t
&>
().
get_impl_ptr
(
std
::
declval
<
PointerType
>
()))
{
// delegate the call to get_impl_ptr<>()
return
get_impl_ptr
(
static_cast
<
PointerType
>
(
nullptr
));
}
@throw what @ref json_serializer<ValueType> `from_json()` method throws if conversion is required
/*!
@brief get a pointer value (implicit)
@copydoc get_ptr()
@since version 2.1.0
*/
template
<
typename
PointerType
,
typename
std
::
enable_if
<
std
::
is_pointer
<
PointerType
>::
value
&&
std
::
is_const
<
typename
std
::
remove_pointer
<
PointerType
>::
type
>::
value
,
int
>::
type
=
0
>
constexpr
auto
get_ptr
()
const
noexcept
->
decltype
(
std
::
declval
<
const
basic_json_t
&>
().
get_impl_ptr
(
std
::
declval
<
PointerType
>
()))
template
<
typename
ValueTypeCV
,
typename
ValueType
=
detail
::
uncvref_t
<
ValueTypeCV
>>
constexpr
auto
get
()
const
noexcept
(
noexcept
(
get_impl
<
ValueType
>
(
detail
::
priority_tag
<
4
>
{})))
->
decltype
(
get_impl
<
ValueType
>
(
detail
::
priority_tag
<
4
>
{}))
{
// delegate the call to get_impl_ptr<>() const
return
get_impl_ptr
(
static_cast
<
PointerType
>
(
nullptr
));
// we cannot static_assert on ValueTypeCV being non-const, because
// there is support for get<const basic_json_t>(), which is why we
// still need the uncvref
static_assert
(
!
std
::
is_reference
<
ValueTypeCV
>::
value
,
"get() cannot be used with reference types, you might want to use get_ref()"
);
return
get_impl
<
ValueType
>
(
detail
::
priority_tag
<
4
>
{});
}
/*!
...
...
@@ -3140,15 +3108,73 @@ class basic_json
}
/*!
@brief get a pointer value (explicit)
@copydoc get()
@brief get a value (explicit)
Explicit type conversion between the JSON value and a compatible value.
The value is filled into the input parameter by calling the @ref json_serializer<ValueType>
`from_json()` method.
The function is equivalent to executing
@code {.cpp}
ValueType v;
JSONSerializer<ValueType>::from_json(*this, v);
@endcode
This overloads is chosen if:
- @a ValueType is not @ref basic_json,
- @ref json_serializer<ValueType> has a `from_json()` method of the form
`void from_json(const basic_json&, ValueType&)`, and
@tparam ValueType the input parameter type.
@return the input parameter, allowing chaining calls.
@throw what @ref json_serializer<ValueType> `from_json()` method throws
@liveexample{The example below shows several conversions from JSON values
to other types. There a few things to note: (1) Floating-point numbers can
be converted to integers\, (2) A JSON array can be converted to a standard
`std::vector<short>`\, (3) A JSON object can be converted to C++
associative containers such as `std::unordered_map<std::string\,
json>`.,get_to}
@since version 3.3.0
*/
template
<
typename
PointerType
,
typename
std
::
enable_if
<
std
::
is_pointer
<
PointerType
>::
value
,
int
>::
type
=
0
>
constexpr
auto
get
()
const
noexcept
->
decltype
(
std
::
declval
<
const
basic_json_t
&>
().
template
get_ptr
<
PointerType
>
())
template
<
typename
ValueType
,
detail
::
enable_if_t
<
!
detail
::
is_basic_json
<
ValueType
>::
value
&&
detail
::
has_from_json
<
basic_json_t
,
ValueType
>::
value
,
int
>
=
0
>
ValueType
&
get_to
(
ValueType
&
v
)
const
noexcept
(
noexcept
(
JSONSerializer
<
ValueType
>::
from_json
(
std
::
declval
<
const
basic_json_t
&>
(),
v
)))
{
// delegate the call to get_ptr
return
get_ptr
<
PointerType
>
();
JSONSerializer
<
ValueType
>::
from_json
(
*
this
,
v
);
return
v
;
}
// specialization to allow to call get_to with a basic_json value
// see https://github.com/nlohmann/json/issues/2175
template
<
typename
ValueType
,
detail
::
enable_if_t
<
detail
::
is_basic_json
<
ValueType
>::
value
,
int
>
=
0
>
ValueType
&
get_to
(
ValueType
&
v
)
const
{
v
=
*
this
;
return
v
;
}
template
<
typename
T
,
std
::
size_t
N
,
typename
Array
=
T
(
&
)[
N
],
detail
::
enable_if_t
<
detail
::
has_from_json
<
basic_json_t
,
Array
>::
value
,
int
>
=
0
>
Array
get_to
(
T
(
&
v
)[
N
])
const
noexcept
(
noexcept
(
JSONSerializer
<
Array
>::
from_json
(
std
::
declval
<
const
basic_json_t
&>
(),
v
)))
{
JSONSerializer
<
Array
>::
from_json
(
*
this
,
v
);
return
v
;
}
/*!
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment