blob: d331612aae7d66ad0abe91653915b2347d0aab10 [file] [log] [blame]
Ed Tanous3dac7492017-08-02 13:46:20 -07001/*
2 __ _____ _____ _____
3 __| | __| | | | JSON for Modern C++
4| | |__ | | | | | | version 2.1.1
5|_____|_____|_____|_|___| https://github.com/nlohmann/json
6
7Licensed under the MIT License <http://opensource.org/licenses/MIT>.
8Copyright (c) 2013-2017 Niels Lohmann <http://nlohmann.me>.
9
10Permission is hereby granted, free of charge, to any person obtaining a copy
11of this software and associated documentation files (the "Software"), to deal
12in the Software without restriction, including without limitation the rights
13to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
14copies of the Software, and to permit persons to whom the Software is
15furnished to do so, subject to the following conditions:
16
17The above copyright notice and this permission notice shall be included in all
18copies or substantial portions of the Software.
19
20THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
21IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
22FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
23AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
24LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
25OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
26SOFTWARE.
27*/
28
29#ifndef NLOHMANN_JSON_HPP
30#define NLOHMANN_JSON_HPP
31
Ed Tanousba9f9a62017-10-11 16:40:35 -070032#include <algorithm> // all_of, copy, fill, find, for_each, generate_n, none_of, remove, reverse, transform
Ed Tanous3dac7492017-08-02 13:46:20 -070033#include <array> // array
34#include <cassert> // assert
Ed Tanous3dac7492017-08-02 13:46:20 -070035#include <ciso646> // and, not, or
Ed Tanousba9f9a62017-10-11 16:40:35 -070036#include <clocale> // lconv, localeconv
Ed Tanous3dac7492017-08-02 13:46:20 -070037#include <cmath> // isfinite, labs, ldexp, signbit
38#include <cstddef> // nullptr_t, ptrdiff_t, size_t
39#include <cstdint> // int64_t, uint64_t
40#include <cstdlib> // abort, strtod, strtof, strtold, strtoul, strtoll, strtoull
Ed Tanousba9f9a62017-10-11 16:40:35 -070041#include <cstring> // memcpy, strlen
Ed Tanous3dac7492017-08-02 13:46:20 -070042#include <forward_list> // forward_list
43#include <functional> // function, hash, less
44#include <initializer_list> // initializer_list
Ed Tanousba9f9a62017-10-11 16:40:35 -070045#include <iomanip> // hex
46#include <iosfwd> // istream, ostream
Ed Tanous3dac7492017-08-02 13:46:20 -070047#include <iterator> // advance, begin, back_inserter, bidirectional_iterator_tag, distance, end, inserter, iterator, iterator_traits, next, random_access_iterator_tag, reverse_iterator
48#include <limits> // numeric_limits
49#include <locale> // locale
50#include <map> // map
51#include <memory> // addressof, allocator, allocator_traits, unique_ptr
52#include <numeric> // accumulate
53#include <sstream> // stringstream
Ed Tanous3dac7492017-08-02 13:46:20 -070054#include <string> // getline, stoi, string, to_string
55#include <type_traits> // add_pointer, conditional, decay, enable_if, false_type, integral_constant, is_arithmetic, is_base_of, is_const, is_constructible, is_convertible, is_default_constructible, is_enum, is_floating_point, is_integral, is_nothrow_move_assignable, is_nothrow_move_constructible, is_pointer, is_reference, is_same, is_scalar, is_signed, remove_const, remove_cv, remove_pointer, remove_reference, true_type, underlying_type
56#include <utility> // declval, forward, make_pair, move, pair, swap
Ed Tanousba9f9a62017-10-11 16:40:35 -070057#include <valarray> // valarray
Ed Tanous3dac7492017-08-02 13:46:20 -070058#include <vector> // vector
59
60// exclude unsupported compilers
61#if defined(__clang__)
62 #if (__clang_major__ * 10000 + __clang_minor__ * 100 + __clang_patchlevel__) < 30400
63 #error "unsupported Clang version - see https://github.com/nlohmann/json#supported-compilers"
64 #endif
Ed Tanousba9f9a62017-10-11 16:40:35 -070065#elif defined(__GNUC__) && !(defined(__ICC) || defined(__INTEL_COMPILER))
Ed Tanous3dac7492017-08-02 13:46:20 -070066 #if (__GNUC__ * 10000 + __GNUC_MINOR__ * 100 + __GNUC_PATCHLEVEL__) < 40900
67 #error "unsupported GCC version - see https://github.com/nlohmann/json#supported-compilers"
68 #endif
69#endif
70
71// disable float-equal warnings on GCC/clang
72#if defined(__clang__) || defined(__GNUC__) || defined(__GNUG__)
73 #pragma GCC diagnostic push
74 #pragma GCC diagnostic ignored "-Wfloat-equal"
75#endif
76
77// disable documentation warnings on clang
78#if defined(__clang__)
79 #pragma GCC diagnostic push
80 #pragma GCC diagnostic ignored "-Wdocumentation"
81#endif
82
83// allow for portable deprecation warnings
84#if defined(__clang__) || defined(__GNUC__) || defined(__GNUG__)
85 #define JSON_DEPRECATED __attribute__((deprecated))
86#elif defined(_MSC_VER)
87 #define JSON_DEPRECATED __declspec(deprecated)
88#else
89 #define JSON_DEPRECATED
90#endif
91
92// allow to disable exceptions
Ed Tanousba9f9a62017-10-11 16:40:35 -070093#if (defined(__cpp_exceptions) || defined(__EXCEPTIONS) || defined(_CPPUNWIND)) && not defined(JSON_NOEXCEPTION)
Ed Tanous3dac7492017-08-02 13:46:20 -070094 #define JSON_THROW(exception) throw exception
95 #define JSON_TRY try
96 #define JSON_CATCH(exception) catch(exception)
97#else
98 #define JSON_THROW(exception) std::abort()
99 #define JSON_TRY if(true)
100 #define JSON_CATCH(exception) if(false)
101#endif
102
Ed Tanousba9f9a62017-10-11 16:40:35 -0700103// manual branch prediction
104#if defined(__clang__) || defined(__GNUC__) || defined(__GNUG__)
105 #define JSON_LIKELY(x) __builtin_expect(!!(x), 1)
106 #define JSON_UNLIKELY(x) __builtin_expect(!!(x), 0)
107#else
108 #define JSON_LIKELY(x) x
109 #define JSON_UNLIKELY(x) x
110#endif
111
Ed Tanous3dac7492017-08-02 13:46:20 -0700112/*!
113@brief namespace for Niels Lohmann
114@see https://github.com/nlohmann
115@since version 1.0.0
116*/
117namespace nlohmann
118{
Ed Tanousba9f9a62017-10-11 16:40:35 -0700119template<typename = void, typename = void>
120struct adl_serializer;
121
122// forward declaration of basic_json (required to split the class)
123template<template<typename U, typename V, typename... Args> class ObjectType =
124 std::map,
125 template<typename U, typename... Args> class ArrayType = std::vector,
126 class StringType = std::string, class BooleanType = bool,
127 class NumberIntegerType = std::int64_t,
128 class NumberUnsignedType = std::uint64_t,
129 class NumberFloatType = double,
130 template<typename U> class AllocatorType = std::allocator,
131 template<typename T, typename SFINAE = void> class JSONSerializer =
132 adl_serializer>
133class basic_json;
134
135// Ugly macros to avoid uglier copy-paste when specializing basic_json
136// This is only temporary and will be removed in 3.0
137
138#define NLOHMANN_BASIC_JSON_TPL_DECLARATION \
139 template<template<typename, typename, typename...> class ObjectType, \
140 template<typename, typename...> class ArrayType, \
141 class StringType, class BooleanType, class NumberIntegerType, \
142 class NumberUnsignedType, class NumberFloatType, \
143 template<typename> class AllocatorType, \
144 template<typename, typename = void> class JSONSerializer>
145
146#define NLOHMANN_BASIC_JSON_TPL \
147 basic_json<ObjectType, ArrayType, StringType, BooleanType, \
148 NumberIntegerType, NumberUnsignedType, NumberFloatType, \
149 AllocatorType, JSONSerializer>
150
Ed Tanous3dac7492017-08-02 13:46:20 -0700151
152/*!
153@brief unnamed namespace with internal helper functions
154
155This namespace collects some functions that could not be defined inside the
156@ref basic_json class.
157
158@since version 2.1.0
159*/
160namespace detail
161{
Ed Tanousba9f9a62017-10-11 16:40:35 -0700162////////////////
163// exceptions //
164////////////////
165
166/*!
167@brief general exception of the @ref basic_json class
168
169This class is an extension of `std::exception` objects with a member @a id for
170exception ids. It is used as the base class for all exceptions thrown by the
171@ref basic_json class. This class can hence be used as "wildcard" to catch
172exceptions.
173
174Subclasses:
175- @ref parse_error for exceptions indicating a parse error
176- @ref invalid_iterator for exceptions indicating errors with iterators
177- @ref type_error for exceptions indicating executing a member function with
178 a wrong type
179- @ref out_of_range for exceptions indicating access out of the defined range
180- @ref other_error for exceptions indicating other library errors
181
182@internal
183@note To have nothrow-copy-constructible exceptions, we internally use
184 `std::runtime_error` which can cope with arbitrary-length error messages.
185 Intermediate strings are built with static functions and then passed to
186 the actual constructor.
187@endinternal
188
189@liveexample{The following code shows how arbitrary library exceptions can be
190caught.,exception}
191
192@since version 3.0.0
193*/
194class exception : public std::exception
195{
196 public:
197 /// returns the explanatory string
198 const char* what() const noexcept override
199 {
200 return m.what();
201 }
202
203 /// the id of the exception
204 const int id;
205
206 protected:
207 exception(int id_, const char* what_arg) : id(id_), m(what_arg) {}
208
209 static std::string name(const std::string& ename, int id_)
210 {
211 return "[json.exception." + ename + "." + std::to_string(id_) + "] ";
212 }
213
214 private:
215 /// an exception object as storage for error messages
216 std::runtime_error m;
217};
218
219/*!
220@brief exception indicating a parse error
221
222This excpetion is thrown by the library when a parse error occurs. Parse errors
223can occur during the deserialization of JSON text, CBOR, MessagePack, as well
224as when using JSON Patch.
225
226Member @a byte holds the byte index of the last read character in the input
227file.
228
229Exceptions have ids 1xx.
230
231name / id | example message | description
232------------------------------ | --------------- | -------------------------
233json.exception.parse_error.101 | parse error at 2: unexpected end of input; expected string literal | This error indicates a syntax error while deserializing a JSON text. The error message describes that an unexpected token (character) was encountered, and the member @a byte indicates the error position.
234json.exception.parse_error.102 | parse error at 14: missing or wrong low surrogate | JSON uses the `\uxxxx` format to describe Unicode characters. Code points above above 0xFFFF are split into two `\uxxxx` entries ("surrogate pairs"). This error indicates that the surrogate pair is incomplete or contains an invalid code point.
235json.exception.parse_error.103 | parse error: code points above 0x10FFFF are invalid | Unicode supports code points up to 0x10FFFF. Code points above 0x10FFFF are invalid.
236json.exception.parse_error.104 | parse error: JSON patch must be an array of objects | [RFC 6902](https://tools.ietf.org/html/rfc6902) requires a JSON Patch document to be a JSON document that represents an array of objects.
237json.exception.parse_error.105 | parse error: operation must have string member 'op' | An operation of a JSON Patch document must contain exactly one "op" member, whose value indicates the operation to perform. Its value must be one of "add", "remove", "replace", "move", "copy", or "test"; other values are errors.
238json.exception.parse_error.106 | parse error: array index '01' must not begin with '0' | An array index in a JSON Pointer ([RFC 6901](https://tools.ietf.org/html/rfc6901)) may be `0` or any number wihtout a leading `0`.
239json.exception.parse_error.107 | parse error: JSON pointer must be empty or begin with '/' - was: 'foo' | A JSON Pointer must be a Unicode string containing a sequence of zero or more reference tokens, each prefixed by a `/` character.
240json.exception.parse_error.108 | parse error: escape character '~' must be followed with '0' or '1' | In a JSON Pointer, only `~0` and `~1` are valid escape sequences.
241json.exception.parse_error.109 | parse error: array index 'one' is not a number | A JSON Pointer array index must be a number.
242json.exception.parse_error.110 | parse error at 1: cannot read 2 bytes from vector | When parsing CBOR or MessagePack, the byte vector ends before the complete value has been read.
243json.exception.parse_error.112 | parse error at 1: error reading CBOR; last byte: 0xf8 | Not all types of CBOR or MessagePack are supported. This exception occurs if an unsupported byte was read.
244json.exception.parse_error.113 | parse error at 2: expected a CBOR string; last byte: 0x98 | While parsing a map key, a value that is not a string has been read.
245
246@note For an input with n bytes, 1 is the index of the first character and n+1
247 is the index of the terminating null byte or the end of file. This also
248 holds true when reading a byte vector (CBOR or MessagePack).
249
250@liveexample{The following code shows how a `parse_error` exception can be
251caught.,parse_error}
252
253@sa @ref exception for the base class of the library exceptions
254@sa @ref invalid_iterator for exceptions indicating errors with iterators
255@sa @ref type_error for exceptions indicating executing a member function with
256 a wrong type
257@sa @ref out_of_range for exceptions indicating access out of the defined range
258@sa @ref other_error for exceptions indicating other library errors
259
260@since version 3.0.0
261*/
262class parse_error : public exception
263{
264 public:
265 /*!
266 @brief create a parse error exception
267 @param[in] id_ the id of the exception
268 @param[in] byte_ the byte index where the error occurred (or 0 if the
269 position cannot be determined)
270 @param[in] what_arg the explanatory string
271 @return parse_error object
272 */
273 static parse_error create(int id_, std::size_t byte_, const std::string& what_arg)
274 {
275 std::string w = exception::name("parse_error", id_) + "parse error" +
276 (byte_ != 0 ? (" at " + std::to_string(byte_)) : "") +
277 ": " + what_arg;
278 return parse_error(id_, byte_, w.c_str());
279 }
280
281 /*!
282 @brief byte index of the parse error
283
284 The byte index of the last read character in the input file.
285
286 @note For an input with n bytes, 1 is the index of the first character and
287 n+1 is the index of the terminating null byte or the end of file.
288 This also holds true when reading a byte vector (CBOR or MessagePack).
289 */
290 const std::size_t byte;
291
292 private:
293 parse_error(int id_, std::size_t byte_, const char* what_arg)
294 : exception(id_, what_arg), byte(byte_) {}
295};
296
297/*!
298@brief exception indicating errors with iterators
299
300This exception is thrown if iterators passed to a library function do not match
301the expected semantics.
302
303Exceptions have ids 2xx.
304
305name / id | example message | description
306----------------------------------- | --------------- | -------------------------
307json.exception.invalid_iterator.201 | iterators are not compatible | The iterators passed to constructor @ref basic_json(InputIT first, InputIT last) are not compatible, meaning they do not belong to the same container. Therefore, the range (@a first, @a last) is invalid.
308json.exception.invalid_iterator.202 | iterator does not fit current value | In an erase or insert function, the passed iterator @a pos does not belong to the JSON value for which the function was called. It hence does not define a valid position for the deletion/insertion.
309json.exception.invalid_iterator.203 | iterators do not fit current value | Either iterator passed to function @ref erase(IteratorType first, IteratorType last) does not belong to the JSON value from which values shall be erased. It hence does not define a valid range to delete values from.
310json.exception.invalid_iterator.204 | iterators out of range | When an iterator range for a primitive type (number, boolean, or string) is passed to a constructor or an erase function, this range has to be exactly (@ref begin(), @ref end()), because this is the only way the single stored value is expressed. All other ranges are invalid.
311json.exception.invalid_iterator.205 | iterator out of range | When an iterator for a primitive type (number, boolean, or string) is passed to an erase function, the iterator has to be the @ref begin() iterator, because it is the only way to address the stored value. All other iterators are invalid.
312json.exception.invalid_iterator.206 | cannot construct with iterators from null | The iterators passed to constructor @ref basic_json(InputIT first, InputIT last) belong to a JSON null value and hence to not define a valid range.
313json.exception.invalid_iterator.207 | cannot use key() for non-object iterators | The key() member function can only be used on iterators belonging to a JSON object, because other types do not have a concept of a key.
314json.exception.invalid_iterator.208 | cannot use operator[] for object iterators | The operator[] to specify a concrete offset cannot be used on iterators belonging to a JSON object, because JSON objects are unordered.
315json.exception.invalid_iterator.209 | cannot use offsets with object iterators | The offset operators (+, -, +=, -=) cannot be used on iterators belonging to a JSON object, because JSON objects are unordered.
316json.exception.invalid_iterator.210 | iterators do not fit | The iterator range passed to the insert function are not compatible, meaning they do not belong to the same container. Therefore, the range (@a first, @a last) is invalid.
317json.exception.invalid_iterator.211 | passed iterators may not belong to container | The iterator range passed to the insert function must not be a subrange of the container to insert to.
318json.exception.invalid_iterator.212 | cannot compare iterators of different containers | When two iterators are compared, they must belong to the same container.
319json.exception.invalid_iterator.213 | cannot compare order of object iterators | The order of object iterators cannot be compared, because JSON objects are unordered.
320json.exception.invalid_iterator.214 | cannot get value | Cannot get value for iterator: Either the iterator belongs to a null value or it is an iterator to a primitive type (number, boolean, or string), but the iterator is different to @ref begin().
321
322@liveexample{The following code shows how an `invalid_iterator` exception can be
323caught.,invalid_iterator}
324
325@sa @ref exception for the base class of the library exceptions
326@sa @ref parse_error for exceptions indicating a parse error
327@sa @ref type_error for exceptions indicating executing a member function with
328 a wrong type
329@sa @ref out_of_range for exceptions indicating access out of the defined range
330@sa @ref other_error for exceptions indicating other library errors
331
332@since version 3.0.0
333*/
334class invalid_iterator : public exception
335{
336 public:
337 static invalid_iterator create(int id_, const std::string& what_arg)
338 {
339 std::string w = exception::name("invalid_iterator", id_) + what_arg;
340 return invalid_iterator(id_, w.c_str());
341 }
342
343 private:
344 invalid_iterator(int id_, const char* what_arg)
345 : exception(id_, what_arg) {}
346};
347
348/*!
349@brief exception indicating executing a member function with a wrong type
350
351This exception is thrown in case of a type error; that is, a library function is
352executed on a JSON value whose type does not match the expected semantics.
353
354Exceptions have ids 3xx.
355
356name / id | example message | description
357----------------------------- | --------------- | -------------------------
358json.exception.type_error.301 | cannot create object from initializer list | To create an object from an initializer list, the initializer list must consist only of a list of pairs whose first element is a string. When this constraint is violated, an array is created instead.
359json.exception.type_error.302 | type must be object, but is array | During implicit or explicit value conversion, the JSON type must be compatible to the target type. For instance, a JSON string can only be converted into string types, but not into numbers or boolean types.
360json.exception.type_error.303 | incompatible ReferenceType for get_ref, actual type is object | To retrieve a reference to a value stored in a @ref basic_json object with @ref get_ref, the type of the reference must match the value type. For instance, for a JSON array, the @a ReferenceType must be @ref array_t&.
361json.exception.type_error.304 | cannot use at() with string | The @ref at() member functions can only be executed for certain JSON types.
362json.exception.type_error.305 | cannot use operator[] with string | The @ref operator[] member functions can only be executed for certain JSON types.
363json.exception.type_error.306 | cannot use value() with string | The @ref value() member functions can only be executed for certain JSON types.
364json.exception.type_error.307 | cannot use erase() with string | The @ref erase() member functions can only be executed for certain JSON types.
365json.exception.type_error.308 | cannot use push_back() with string | The @ref push_back() and @ref operator+= member functions can only be executed for certain JSON types.
366json.exception.type_error.309 | cannot use insert() with | The @ref insert() member functions can only be executed for certain JSON types.
367json.exception.type_error.310 | cannot use swap() with number | The @ref swap() member functions can only be executed for certain JSON types.
368json.exception.type_error.311 | cannot use emplace_back() with string | The @ref emplace_back() member function can only be executed for certain JSON types.
369json.exception.type_error.312 | cannot use update() with string | The @ref update() member functions can only be executed for certain JSON types.
370json.exception.type_error.313 | invalid value to unflatten | The @ref unflatten function converts an object whose keys are JSON Pointers back into an arbitrary nested JSON value. The JSON Pointers must not overlap, because then the resulting value would not be well defined.
371json.exception.type_error.314 | only objects can be unflattened | The @ref unflatten function only works for an object whose keys are JSON Pointers.
372json.exception.type_error.315 | values in object must be primitive | The @ref unflatten function only works for an object whose keys are JSON Pointers and whose values are primitive.
373
374@liveexample{The following code shows how a `type_error` exception can be
375caught.,type_error}
376
377@sa @ref exception for the base class of the library exceptions
378@sa @ref parse_error for exceptions indicating a parse error
379@sa @ref invalid_iterator for exceptions indicating errors with iterators
380@sa @ref out_of_range for exceptions indicating access out of the defined range
381@sa @ref other_error for exceptions indicating other library errors
382
383@since version 3.0.0
384*/
385class type_error : public exception
386{
387 public:
388 static type_error create(int id_, const std::string& what_arg)
389 {
390 std::string w = exception::name("type_error", id_) + what_arg;
391 return type_error(id_, w.c_str());
392 }
393
394 private:
395 type_error(int id_, const char* what_arg) : exception(id_, what_arg) {}
396};
397
398/*!
399@brief exception indicating access out of the defined range
400
401This exception is thrown in case a library function is called on an input
402parameter that exceeds the expected range, for instance in case of array
403indices or nonexisting object keys.
404
405Exceptions have ids 4xx.
406
407name / id | example message | description
408------------------------------- | --------------- | -------------------------
409json.exception.out_of_range.401 | array index 3 is out of range | The provided array index @a i is larger than @a size-1.
410json.exception.out_of_range.402 | array index '-' (3) is out of range | The special array index `-` in a JSON Pointer never describes a valid element of the array, but the index past the end. That is, it can only be used to add elements at this position, but not to read it.
411json.exception.out_of_range.403 | key 'foo' not found | The provided key was not found in the JSON object.
412json.exception.out_of_range.404 | unresolved reference token 'foo' | A reference token in a JSON Pointer could not be resolved.
413json.exception.out_of_range.405 | JSON pointer has no parent | The JSON Patch operations 'remove' and 'add' can not be applied to the root element of the JSON value.
414json.exception.out_of_range.406 | number overflow parsing '10E1000' | A parsed number could not be stored as without changing it to NaN or INF.
415
416@liveexample{The following code shows how an `out_of_range` exception can be
417caught.,out_of_range}
418
419@sa @ref exception for the base class of the library exceptions
420@sa @ref parse_error for exceptions indicating a parse error
421@sa @ref invalid_iterator for exceptions indicating errors with iterators
422@sa @ref type_error for exceptions indicating executing a member function with
423 a wrong type
424@sa @ref other_error for exceptions indicating other library errors
425
426@since version 3.0.0
427*/
428class out_of_range : public exception
429{
430 public:
431 static out_of_range create(int id_, const std::string& what_arg)
432 {
433 std::string w = exception::name("out_of_range", id_) + what_arg;
434 return out_of_range(id_, w.c_str());
435 }
436
437 private:
438 out_of_range(int id_, const char* what_arg) : exception(id_, what_arg) {}
439};
440
441/*!
442@brief exception indicating other library errors
443
444This exception is thrown in case of errors that cannot be classified with the
445other exception types.
446
447Exceptions have ids 5xx.
448
449name / id | example message | description
450------------------------------ | --------------- | -------------------------
451json.exception.other_error.501 | unsuccessful: {"op":"test","path":"/baz", "value":"bar"} | A JSON Patch operation 'test' failed. The unsuccessful operation is also printed.
452json.exception.other_error.502 | invalid object size for conversion | Some conversions to user-defined types impose constraints on the object size (e.g. std::pair)
453
454@sa @ref exception for the base class of the library exceptions
455@sa @ref parse_error for exceptions indicating a parse error
456@sa @ref invalid_iterator for exceptions indicating errors with iterators
457@sa @ref type_error for exceptions indicating executing a member function with
458 a wrong type
459@sa @ref out_of_range for exceptions indicating access out of the defined range
460
461@liveexample{The following code shows how an `other_error` exception can be
462caught.,other_error}
463
464@since version 3.0.0
465*/
466class other_error : public exception
467{
468 public:
469 static other_error create(int id_, const std::string& what_arg)
470 {
471 std::string w = exception::name("other_error", id_) + what_arg;
472 return other_error(id_, w.c_str());
473 }
474
475 private:
476 other_error(int id_, const char* what_arg) : exception(id_, what_arg) {}
477};
478
479
480
Ed Tanous3dac7492017-08-02 13:46:20 -0700481///////////////////////////
482// JSON type enumeration //
483///////////////////////////
484
485/*!
486@brief the JSON type enumeration
487
488This enumeration collects the different JSON types. It is internally used to
489distinguish the stored values, and the functions @ref basic_json::is_null(),
490@ref basic_json::is_object(), @ref basic_json::is_array(),
491@ref basic_json::is_string(), @ref basic_json::is_boolean(),
492@ref basic_json::is_number() (with @ref basic_json::is_number_integer(),
493@ref basic_json::is_number_unsigned(), and @ref basic_json::is_number_float()),
494@ref basic_json::is_discarded(), @ref basic_json::is_primitive(), and
495@ref basic_json::is_structured() rely on it.
496
497@note There are three enumeration entries (number_integer, number_unsigned, and
498number_float), because the library distinguishes these three types for numbers:
499@ref basic_json::number_unsigned_t is used for unsigned integers,
500@ref basic_json::number_integer_t is used for signed integers, and
501@ref basic_json::number_float_t is used for floating-point numbers or to
502approximate integers which do not fit in the limits of their respective type.
503
504@sa @ref basic_json::basic_json(const value_t value_type) -- create a JSON
505value with the default value for a given type
506
507@since version 1.0.0
508*/
509enum class value_t : uint8_t
510{
Ed Tanousba9f9a62017-10-11 16:40:35 -0700511 null, ///< null value
512 object, ///< object (unordered set of name/value pairs)
513 array, ///< array (ordered collection of values)
514 string, ///< string value
515 boolean, ///< boolean value
516 number_integer, ///< number value (signed integer)
517 number_unsigned, ///< number value (unsigned integer)
518 number_float, ///< number value (floating-point)
519 discarded ///< discarded by the the parser callback function
Ed Tanous3dac7492017-08-02 13:46:20 -0700520};
521
522/*!
523@brief comparison operator for JSON types
524
525Returns an ordering that is similar to Python:
526- order: null < boolean < number < object < array < string
527- furthermore, each type is not smaller than itself
528
529@since version 1.0.0
530*/
531inline bool operator<(const value_t lhs, const value_t rhs) noexcept
532{
533 static constexpr std::array<uint8_t, 8> order = {{
534 0, // null
535 3, // object
536 4, // array
537 5, // string
538 1, // boolean
539 2, // integer
540 2, // unsigned
541 2, // float
542 }
543 };
544
545 // discarded values are not comparable
Ed Tanousba9f9a62017-10-11 16:40:35 -0700546 return lhs != value_t::discarded and rhs != value_t::discarded and
547 order[static_cast<std::size_t>(lhs)] < order[static_cast<std::size_t>(rhs)];
Ed Tanous3dac7492017-08-02 13:46:20 -0700548}
549
550
551/////////////
552// helpers //
553/////////////
554
Ed Tanousba9f9a62017-10-11 16:40:35 -0700555template<typename> struct is_basic_json : std::false_type {};
556
557NLOHMANN_BASIC_JSON_TPL_DECLARATION
558struct is_basic_json<NLOHMANN_BASIC_JSON_TPL> : std::true_type {};
559
Ed Tanous3dac7492017-08-02 13:46:20 -0700560// alias templates to reduce boilerplate
561template<bool B, typename T = void>
562using enable_if_t = typename std::enable_if<B, T>::type;
563
564template<typename T>
565using uncvref_t = typename std::remove_cv<typename std::remove_reference<T>::type>::type;
566
Ed Tanousba9f9a62017-10-11 16:40:35 -0700567// implementation of C++14 index_sequence and affiliates
568// source: https://stackoverflow.com/a/32223343
569template<std::size_t... Ints>
570struct index_sequence
571{
572 using type = index_sequence;
573 using value_type = std::size_t;
574 static constexpr std::size_t size() noexcept
575 {
576 return sizeof...(Ints);
577 }
578};
579
580template<class Sequence1, class Sequence2>
581struct merge_and_renumber;
582
583template<std::size_t... I1, std::size_t... I2>
584struct merge_and_renumber<index_sequence<I1...>, index_sequence<I2...>>
585 : index_sequence < I1..., (sizeof...(I1) + I2)... >
586 {};
587
588template<std::size_t N>
589struct make_index_sequence
590 : merge_and_renumber < typename make_index_sequence < N / 2 >::type,
591 typename make_index_sequence < N - N / 2 >::type >
592{};
593
594template<> struct make_index_sequence<0> : index_sequence<> { };
595template<> struct make_index_sequence<1> : index_sequence<0> { };
596
597template<typename... Ts>
598using index_sequence_for = make_index_sequence<sizeof...(Ts)>;
Ed Tanous3dac7492017-08-02 13:46:20 -0700599
600/*
601Implementation of two C++17 constructs: conjunction, negation. This is needed
602to avoid evaluating all the traits in a condition
603
604For example: not std::is_same<void, T>::value and has_value_type<T>::value
605will not compile when T = void (on MSVC at least). Whereas
606conjunction<negation<std::is_same<void, T>>, has_value_type<T>>::value will
607stop evaluating if negation<...>::value == false
608
609Please note that those constructs must be used with caution, since symbols can
610become very long quickly (which can slow down compilation and cause MSVC
611internal compiler errors). Only use it when you have to (see example ahead).
612*/
613template<class...> struct conjunction : std::true_type {};
614template<class B1> struct conjunction<B1> : B1 {};
615template<class B1, class... Bn>
616struct conjunction<B1, Bn...> : std::conditional<bool(B1::value), conjunction<Bn...>, B1>::type {};
617
618template<class B> struct negation : std::integral_constant < bool, !B::value > {};
619
620// dispatch utility (taken from ranges-v3)
621template<unsigned N> struct priority_tag : priority_tag < N - 1 > {};
622template<> struct priority_tag<0> {};
623
624
625//////////////////
626// constructors //
627//////////////////
628
629template<value_t> struct external_constructor;
630
631template<>
632struct external_constructor<value_t::boolean>
633{
634 template<typename BasicJsonType>
635 static void construct(BasicJsonType& j, typename BasicJsonType::boolean_t b) noexcept
636 {
637 j.m_type = value_t::boolean;
638 j.m_value = b;
639 j.assert_invariant();
640 }
641};
642
643template<>
644struct external_constructor<value_t::string>
645{
646 template<typename BasicJsonType>
647 static void construct(BasicJsonType& j, const typename BasicJsonType::string_t& s)
648 {
649 j.m_type = value_t::string;
650 j.m_value = s;
651 j.assert_invariant();
652 }
Ed Tanousba9f9a62017-10-11 16:40:35 -0700653
654 template<typename BasicJsonType>
655 static void construct(BasicJsonType& j, typename BasicJsonType::string_t&& s)
656 {
657 j.m_type = value_t::string;
658 j.m_value = std::move(s);
659 j.assert_invariant();
660 }
Ed Tanous3dac7492017-08-02 13:46:20 -0700661};
662
663template<>
664struct external_constructor<value_t::number_float>
665{
666 template<typename BasicJsonType>
667 static void construct(BasicJsonType& j, typename BasicJsonType::number_float_t val) noexcept
668 {
Ed Tanousba9f9a62017-10-11 16:40:35 -0700669 j.m_type = value_t::number_float;
670 j.m_value = val;
Ed Tanous3dac7492017-08-02 13:46:20 -0700671 j.assert_invariant();
672 }
673};
674
675template<>
676struct external_constructor<value_t::number_unsigned>
677{
678 template<typename BasicJsonType>
679 static void construct(BasicJsonType& j, typename BasicJsonType::number_unsigned_t val) noexcept
680 {
681 j.m_type = value_t::number_unsigned;
682 j.m_value = val;
683 j.assert_invariant();
684 }
685};
686
687template<>
688struct external_constructor<value_t::number_integer>
689{
690 template<typename BasicJsonType>
691 static void construct(BasicJsonType& j, typename BasicJsonType::number_integer_t val) noexcept
692 {
693 j.m_type = value_t::number_integer;
694 j.m_value = val;
695 j.assert_invariant();
696 }
697};
698
699template<>
700struct external_constructor<value_t::array>
701{
702 template<typename BasicJsonType>
703 static void construct(BasicJsonType& j, const typename BasicJsonType::array_t& arr)
704 {
705 j.m_type = value_t::array;
706 j.m_value = arr;
707 j.assert_invariant();
708 }
709
Ed Tanousba9f9a62017-10-11 16:40:35 -0700710 template<typename BasicJsonType>
711 static void construct(BasicJsonType& j, typename BasicJsonType::array_t&& arr)
712 {
713 j.m_type = value_t::array;
714 j.m_value = std::move(arr);
715 j.assert_invariant();
716 }
717
Ed Tanous3dac7492017-08-02 13:46:20 -0700718 template<typename BasicJsonType, typename CompatibleArrayType,
719 enable_if_t<not std::is_same<CompatibleArrayType,
720 typename BasicJsonType::array_t>::value,
721 int> = 0>
722 static void construct(BasicJsonType& j, const CompatibleArrayType& arr)
723 {
724 using std::begin;
725 using std::end;
726 j.m_type = value_t::array;
727 j.m_value.array = j.template create<typename BasicJsonType::array_t>(begin(arr), end(arr));
728 j.assert_invariant();
729 }
Ed Tanousba9f9a62017-10-11 16:40:35 -0700730
731 template<typename BasicJsonType>
732 static void construct(BasicJsonType& j, const std::vector<bool>& arr)
733 {
734 j.m_type = value_t::array;
735 j.m_value = value_t::array;
736 j.m_value.array->reserve(arr.size());
737 for (bool x : arr)
738 {
739 j.m_value.array->push_back(x);
740 }
741 j.assert_invariant();
742 }
743
744 template<typename BasicJsonType, typename T,
745 enable_if_t<std::is_convertible<T, BasicJsonType>::value, int> = 0>
746 static void construct(BasicJsonType& j, const std::valarray<T>& arr)
747 {
748 j.m_type = value_t::array;
749 j.m_value = value_t::array;
750 j.m_value.array->resize(arr.size());
751 std::copy(std::begin(arr), std::end(arr), j.m_value.array->begin());
752 j.assert_invariant();
753 }
Ed Tanous3dac7492017-08-02 13:46:20 -0700754};
755
756template<>
757struct external_constructor<value_t::object>
758{
759 template<typename BasicJsonType>
760 static void construct(BasicJsonType& j, const typename BasicJsonType::object_t& obj)
761 {
762 j.m_type = value_t::object;
763 j.m_value = obj;
764 j.assert_invariant();
765 }
766
Ed Tanousba9f9a62017-10-11 16:40:35 -0700767 template<typename BasicJsonType>
768 static void construct(BasicJsonType& j, typename BasicJsonType::object_t&& obj)
769 {
770 j.m_type = value_t::object;
771 j.m_value = std::move(obj);
772 j.assert_invariant();
773 }
774
Ed Tanous3dac7492017-08-02 13:46:20 -0700775 template<typename BasicJsonType, typename CompatibleObjectType,
776 enable_if_t<not std::is_same<CompatibleObjectType,
Ed Tanousba9f9a62017-10-11 16:40:35 -0700777 typename BasicJsonType::object_t>::value, int> = 0>
Ed Tanous3dac7492017-08-02 13:46:20 -0700778 static void construct(BasicJsonType& j, const CompatibleObjectType& obj)
779 {
780 using std::begin;
781 using std::end;
782
783 j.m_type = value_t::object;
784 j.m_value.object = j.template create<typename BasicJsonType::object_t>(begin(obj), end(obj));
785 j.assert_invariant();
786 }
787};
788
789
790////////////////////////
791// has_/is_ functions //
792////////////////////////
793
794/*!
795@brief Helper to determine whether there's a key_type for T.
796
797This helper is used to tell associative containers apart from other containers
798such as sequence containers. For instance, `std::map` passes the test as it
799contains a `mapped_type`, whereas `std::vector` fails the test.
800
801@sa http://stackoverflow.com/a/7728728/266378
802@since version 1.0.0, overworked in version 2.0.6
803*/
804#define NLOHMANN_JSON_HAS_HELPER(type) \
805 template<typename T> struct has_##type { \
806 private: \
807 template<typename U, typename = typename U::type> \
808 static int detect(U &&); \
809 static void detect(...); \
810 public: \
811 static constexpr bool value = \
812 std::is_integral<decltype(detect(std::declval<T>()))>::value; \
813 }
814
815NLOHMANN_JSON_HAS_HELPER(mapped_type);
816NLOHMANN_JSON_HAS_HELPER(key_type);
817NLOHMANN_JSON_HAS_HELPER(value_type);
818NLOHMANN_JSON_HAS_HELPER(iterator);
819
820#undef NLOHMANN_JSON_HAS_HELPER
821
822
823template<bool B, class RealType, class CompatibleObjectType>
824struct is_compatible_object_type_impl : std::false_type {};
825
826template<class RealType, class CompatibleObjectType>
827struct is_compatible_object_type_impl<true, RealType, CompatibleObjectType>
828{
829 static constexpr auto value =
Ed Tanousba9f9a62017-10-11 16:40:35 -0700830 std::is_constructible<typename RealType::key_type, typename CompatibleObjectType::key_type>::value and
831 std::is_constructible<typename RealType::mapped_type, typename CompatibleObjectType::mapped_type>::value;
Ed Tanous3dac7492017-08-02 13:46:20 -0700832};
833
834template<class BasicJsonType, class CompatibleObjectType>
835struct is_compatible_object_type
836{
837 static auto constexpr value = is_compatible_object_type_impl <
838 conjunction<negation<std::is_same<void, CompatibleObjectType>>,
839 has_mapped_type<CompatibleObjectType>,
840 has_key_type<CompatibleObjectType>>::value,
841 typename BasicJsonType::object_t, CompatibleObjectType >::value;
842};
843
844template<typename BasicJsonType, typename T>
845struct is_basic_json_nested_type
846{
847 static auto constexpr value = std::is_same<T, typename BasicJsonType::iterator>::value or
848 std::is_same<T, typename BasicJsonType::const_iterator>::value or
849 std::is_same<T, typename BasicJsonType::reverse_iterator>::value or
Ed Tanousba9f9a62017-10-11 16:40:35 -0700850 std::is_same<T, typename BasicJsonType::const_reverse_iterator>::value;
Ed Tanous3dac7492017-08-02 13:46:20 -0700851};
852
853template<class BasicJsonType, class CompatibleArrayType>
854struct is_compatible_array_type
855{
856 static auto constexpr value =
857 conjunction<negation<std::is_same<void, CompatibleArrayType>>,
858 negation<is_compatible_object_type<
859 BasicJsonType, CompatibleArrayType>>,
860 negation<std::is_constructible<typename BasicJsonType::string_t,
861 CompatibleArrayType>>,
862 negation<is_basic_json_nested_type<BasicJsonType, CompatibleArrayType>>,
863 has_value_type<CompatibleArrayType>,
864 has_iterator<CompatibleArrayType>>::value;
865};
866
867template<bool, typename, typename>
868struct is_compatible_integer_type_impl : std::false_type {};
869
870template<typename RealIntegerType, typename CompatibleNumberIntegerType>
871struct is_compatible_integer_type_impl<true, RealIntegerType, CompatibleNumberIntegerType>
872{
873 // is there an assert somewhere on overflows?
874 using RealLimits = std::numeric_limits<RealIntegerType>;
875 using CompatibleLimits = std::numeric_limits<CompatibleNumberIntegerType>;
876
877 static constexpr auto value =
Ed Tanousba9f9a62017-10-11 16:40:35 -0700878 std::is_constructible<RealIntegerType, CompatibleNumberIntegerType>::value and
Ed Tanous3dac7492017-08-02 13:46:20 -0700879 CompatibleLimits::is_integer and
880 RealLimits::is_signed == CompatibleLimits::is_signed;
881};
882
883template<typename RealIntegerType, typename CompatibleNumberIntegerType>
884struct is_compatible_integer_type
885{
886 static constexpr auto value =
887 is_compatible_integer_type_impl <
888 std::is_integral<CompatibleNumberIntegerType>::value and
889 not std::is_same<bool, CompatibleNumberIntegerType>::value,
890 RealIntegerType, CompatibleNumberIntegerType > ::value;
891};
892
893
894// trait checking if JSONSerializer<T>::from_json(json const&, udt&) exists
895template<typename BasicJsonType, typename T>
896struct has_from_json
897{
898 private:
899 // also check the return type of from_json
900 template<typename U, typename = enable_if_t<std::is_same<void, decltype(uncvref_t<U>::from_json(
901 std::declval<BasicJsonType>(), std::declval<T&>()))>::value>>
902 static int detect(U&&);
903 static void detect(...);
904
905 public:
906 static constexpr bool value = std::is_integral<decltype(
907 detect(std::declval<typename BasicJsonType::template json_serializer<T, void>>()))>::value;
908};
909
910// This trait checks if JSONSerializer<T>::from_json(json const&) exists
911// this overload is used for non-default-constructible user-defined-types
912template<typename BasicJsonType, typename T>
913struct has_non_default_from_json
914{
915 private:
916 template <
917 typename U,
918 typename = enable_if_t<std::is_same<
919 T, decltype(uncvref_t<U>::from_json(std::declval<BasicJsonType>()))>::value >>
920 static int detect(U&&);
921 static void detect(...);
922
923 public:
924 static constexpr bool value = std::is_integral<decltype(detect(
925 std::declval<typename BasicJsonType::template json_serializer<T, void>>()))>::value;
926};
927
928// This trait checks if BasicJsonType::json_serializer<T>::to_json exists
929template<typename BasicJsonType, typename T>
930struct has_to_json
931{
932 private:
933 template<typename U, typename = decltype(uncvref_t<U>::to_json(
934 std::declval<BasicJsonType&>(), std::declval<T>()))>
935 static int detect(U&&);
936 static void detect(...);
937
938 public:
939 static constexpr bool value = std::is_integral<decltype(detect(
940 std::declval<typename BasicJsonType::template json_serializer<T, void>>()))>::value;
941};
942
943
944/////////////
945// to_json //
946/////////////
947
948template<typename BasicJsonType, typename T, enable_if_t<
949 std::is_same<T, typename BasicJsonType::boolean_t>::value, int> = 0>
950void to_json(BasicJsonType& j, T b) noexcept
951{
952 external_constructor<value_t::boolean>::construct(j, b);
953}
954
955template<typename BasicJsonType, typename CompatibleString,
956 enable_if_t<std::is_constructible<typename BasicJsonType::string_t,
957 CompatibleString>::value, int> = 0>
958void to_json(BasicJsonType& j, const CompatibleString& s)
959{
960 external_constructor<value_t::string>::construct(j, s);
961}
962
Ed Tanousba9f9a62017-10-11 16:40:35 -0700963template <typename BasicJsonType>
964void to_json(BasicJsonType& j, typename BasicJsonType::string_t&& s)
965{
966 external_constructor<value_t::string>::construct(j, std::move(s));
967}
968
Ed Tanous3dac7492017-08-02 13:46:20 -0700969template<typename BasicJsonType, typename FloatType,
970 enable_if_t<std::is_floating_point<FloatType>::value, int> = 0>
971void to_json(BasicJsonType& j, FloatType val) noexcept
972{
973 external_constructor<value_t::number_float>::construct(j, static_cast<typename BasicJsonType::number_float_t>(val));
974}
975
976template <
977 typename BasicJsonType, typename CompatibleNumberUnsignedType,
978 enable_if_t<is_compatible_integer_type<typename BasicJsonType::number_unsigned_t,
979 CompatibleNumberUnsignedType>::value, int> = 0 >
980void to_json(BasicJsonType& j, CompatibleNumberUnsignedType val) noexcept
981{
982 external_constructor<value_t::number_unsigned>::construct(j, static_cast<typename BasicJsonType::number_unsigned_t>(val));
983}
984
985template <
986 typename BasicJsonType, typename CompatibleNumberIntegerType,
987 enable_if_t<is_compatible_integer_type<typename BasicJsonType::number_integer_t,
988 CompatibleNumberIntegerType>::value, int> = 0 >
989void to_json(BasicJsonType& j, CompatibleNumberIntegerType val) noexcept
990{
991 external_constructor<value_t::number_integer>::construct(j, static_cast<typename BasicJsonType::number_integer_t>(val));
992}
993
Ed Tanousba9f9a62017-10-11 16:40:35 -0700994template<typename BasicJsonType, typename EnumType,
995 enable_if_t<std::is_enum<EnumType>::value, int> = 0>
996void to_json(BasicJsonType& j, EnumType e) noexcept
Ed Tanous3dac7492017-08-02 13:46:20 -0700997{
Ed Tanousba9f9a62017-10-11 16:40:35 -0700998 using underlying_type = typename std::underlying_type<EnumType>::type;
999 external_constructor<value_t::number_integer>::construct(j, static_cast<underlying_type>(e));
1000}
1001
1002template<typename BasicJsonType>
1003void to_json(BasicJsonType& j, const std::vector<bool>& e)
1004{
1005 external_constructor<value_t::array>::construct(j, e);
Ed Tanous3dac7492017-08-02 13:46:20 -07001006}
1007
1008template <
1009 typename BasicJsonType, typename CompatibleArrayType,
1010 enable_if_t <
1011 is_compatible_array_type<BasicJsonType, CompatibleArrayType>::value or
1012 std::is_same<typename BasicJsonType::array_t, CompatibleArrayType>::value,
1013 int > = 0 >
Ed Tanousba9f9a62017-10-11 16:40:35 -07001014void to_json(BasicJsonType& j, const CompatibleArrayType& arr)
Ed Tanous3dac7492017-08-02 13:46:20 -07001015{
1016 external_constructor<value_t::array>::construct(j, arr);
1017}
1018
Ed Tanousba9f9a62017-10-11 16:40:35 -07001019template <typename BasicJsonType, typename T,
1020 enable_if_t<std::is_convertible<T, BasicJsonType>::value, int> = 0>
1021void to_json(BasicJsonType& j, std::valarray<T> arr)
1022{
1023 external_constructor<value_t::array>::construct(j, std::move(arr));
1024}
1025
1026template <typename BasicJsonType>
1027void to_json(BasicJsonType& j, typename BasicJsonType::array_t&& arr)
1028{
1029 external_constructor<value_t::array>::construct(j, std::move(arr));
1030}
1031
Ed Tanous3dac7492017-08-02 13:46:20 -07001032template <
1033 typename BasicJsonType, typename CompatibleObjectType,
1034 enable_if_t<is_compatible_object_type<BasicJsonType, CompatibleObjectType>::value,
1035 int> = 0 >
Ed Tanousba9f9a62017-10-11 16:40:35 -07001036void to_json(BasicJsonType& j, const CompatibleObjectType& obj)
Ed Tanous3dac7492017-08-02 13:46:20 -07001037{
Ed Tanousba9f9a62017-10-11 16:40:35 -07001038 external_constructor<value_t::object>::construct(j, obj);
Ed Tanous3dac7492017-08-02 13:46:20 -07001039}
1040
Ed Tanousba9f9a62017-10-11 16:40:35 -07001041template <typename BasicJsonType>
1042void to_json(BasicJsonType& j, typename BasicJsonType::object_t&& obj)
1043{
1044 external_constructor<value_t::object>::construct(j, std::move(obj));
1045}
1046
1047template<typename BasicJsonType, typename T, std::size_t N,
1048 enable_if_t<not std::is_constructible<
1049 typename BasicJsonType::string_t, T (&)[N]>::value,
1050 int> = 0>
1051void to_json(BasicJsonType& j, T (&arr)[N])
1052{
1053 external_constructor<value_t::array>::construct(j, arr);
1054}
1055
1056template<typename BasicJsonType, typename... Args>
1057void to_json(BasicJsonType& j, const std::pair<Args...>& p)
1058{
1059 j = {p.first, p.second};
1060}
1061
1062template<typename BasicJsonType, typename Tuple, std::size_t... Idx>
1063void to_json_tuple_impl(BasicJsonType& j, const Tuple& t, index_sequence<Idx...>)
1064{
1065 j = {std::get<Idx>(t)...};
1066}
1067
1068template<typename BasicJsonType, typename... Args>
1069void to_json(BasicJsonType& j, const std::tuple<Args...>& t)
1070{
1071 to_json_tuple_impl(j, t, index_sequence_for<Args...> {});
1072}
Ed Tanous3dac7492017-08-02 13:46:20 -07001073
1074///////////////
1075// from_json //
1076///////////////
1077
1078// overloads for basic_json template parameters
1079template<typename BasicJsonType, typename ArithmeticType,
1080 enable_if_t<std::is_arithmetic<ArithmeticType>::value and
1081 not std::is_same<ArithmeticType,
1082 typename BasicJsonType::boolean_t>::value,
1083 int> = 0>
1084void get_arithmetic_value(const BasicJsonType& j, ArithmeticType& val)
1085{
1086 switch (static_cast<value_t>(j))
1087 {
1088 case value_t::number_unsigned:
1089 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07001090 val = static_cast<ArithmeticType>(*j.template get_ptr<const typename BasicJsonType::number_unsigned_t*>());
Ed Tanous3dac7492017-08-02 13:46:20 -07001091 break;
1092 }
1093 case value_t::number_integer:
1094 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07001095 val = static_cast<ArithmeticType>(*j.template get_ptr<const typename BasicJsonType::number_integer_t*>());
Ed Tanous3dac7492017-08-02 13:46:20 -07001096 break;
1097 }
1098 case value_t::number_float:
1099 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07001100 val = static_cast<ArithmeticType>(*j.template get_ptr<const typename BasicJsonType::number_float_t*>());
Ed Tanous3dac7492017-08-02 13:46:20 -07001101 break;
1102 }
Ed Tanousba9f9a62017-10-11 16:40:35 -07001103
Ed Tanous3dac7492017-08-02 13:46:20 -07001104 default:
Ed Tanousba9f9a62017-10-11 16:40:35 -07001105 JSON_THROW(type_error::create(302, "type must be number, but is " + std::string(j.type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07001106 }
1107}
1108
1109template<typename BasicJsonType>
1110void from_json(const BasicJsonType& j, typename BasicJsonType::boolean_t& b)
1111{
Ed Tanousba9f9a62017-10-11 16:40:35 -07001112 if (JSON_UNLIKELY(not j.is_boolean()))
Ed Tanous3dac7492017-08-02 13:46:20 -07001113 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07001114 JSON_THROW(type_error::create(302, "type must be boolean, but is " + std::string(j.type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07001115 }
1116 b = *j.template get_ptr<const typename BasicJsonType::boolean_t*>();
1117}
1118
1119template<typename BasicJsonType>
1120void from_json(const BasicJsonType& j, typename BasicJsonType::string_t& s)
1121{
Ed Tanousba9f9a62017-10-11 16:40:35 -07001122 if (JSON_UNLIKELY(not j.is_string()))
Ed Tanous3dac7492017-08-02 13:46:20 -07001123 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07001124 JSON_THROW(type_error::create(302, "type must be string, but is " + std::string(j.type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07001125 }
1126 s = *j.template get_ptr<const typename BasicJsonType::string_t*>();
1127}
1128
1129template<typename BasicJsonType>
1130void from_json(const BasicJsonType& j, typename BasicJsonType::number_float_t& val)
1131{
1132 get_arithmetic_value(j, val);
1133}
1134
1135template<typename BasicJsonType>
1136void from_json(const BasicJsonType& j, typename BasicJsonType::number_unsigned_t& val)
1137{
1138 get_arithmetic_value(j, val);
1139}
1140
1141template<typename BasicJsonType>
1142void from_json(const BasicJsonType& j, typename BasicJsonType::number_integer_t& val)
1143{
1144 get_arithmetic_value(j, val);
1145}
1146
Ed Tanousba9f9a62017-10-11 16:40:35 -07001147template<typename BasicJsonType, typename EnumType,
1148 enable_if_t<std::is_enum<EnumType>::value, int> = 0>
1149void from_json(const BasicJsonType& j, EnumType& e)
Ed Tanous3dac7492017-08-02 13:46:20 -07001150{
Ed Tanousba9f9a62017-10-11 16:40:35 -07001151 typename std::underlying_type<EnumType>::type val;
Ed Tanous3dac7492017-08-02 13:46:20 -07001152 get_arithmetic_value(j, val);
Ed Tanousba9f9a62017-10-11 16:40:35 -07001153 e = static_cast<EnumType>(val);
Ed Tanous3dac7492017-08-02 13:46:20 -07001154}
1155
1156template<typename BasicJsonType>
1157void from_json(const BasicJsonType& j, typename BasicJsonType::array_t& arr)
1158{
Ed Tanousba9f9a62017-10-11 16:40:35 -07001159 if (JSON_UNLIKELY(not j.is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -07001160 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07001161 JSON_THROW(type_error::create(302, "type must be array, but is " + std::string(j.type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07001162 }
1163 arr = *j.template get_ptr<const typename BasicJsonType::array_t*>();
1164}
1165
1166// forward_list doesn't have an insert method
Ed Tanousba9f9a62017-10-11 16:40:35 -07001167template<typename BasicJsonType, typename T, typename Allocator,
1168 enable_if_t<std::is_convertible<BasicJsonType, T>::value, int> = 0>
Ed Tanous3dac7492017-08-02 13:46:20 -07001169void from_json(const BasicJsonType& j, std::forward_list<T, Allocator>& l)
1170{
Ed Tanousba9f9a62017-10-11 16:40:35 -07001171 if (JSON_UNLIKELY(not j.is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -07001172 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07001173 JSON_THROW(type_error::create(302, "type must be array, but is " + std::string(j.type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07001174 }
Ed Tanousba9f9a62017-10-11 16:40:35 -07001175 std::transform(j.rbegin(), j.rend(),
1176 std::front_inserter(l), [](const BasicJsonType & i)
Ed Tanous3dac7492017-08-02 13:46:20 -07001177 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07001178 return i.template get<T>();
1179 });
1180}
1181
1182// valarray doesn't have an insert method
1183template<typename BasicJsonType, typename T,
1184 enable_if_t<std::is_convertible<BasicJsonType, T>::value, int> = 0>
1185void from_json(const BasicJsonType& j, std::valarray<T>& l)
1186{
1187 if (JSON_UNLIKELY(not j.is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -07001188 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07001189 JSON_THROW(type_error::create(302, "type must be array, but is " + std::string(j.type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07001190 }
Ed Tanousba9f9a62017-10-11 16:40:35 -07001191 l.resize(j.size());
1192 std::copy(j.m_value.array->begin(), j.m_value.array->end(), std::begin(l));
Ed Tanous3dac7492017-08-02 13:46:20 -07001193}
1194
1195template<typename BasicJsonType, typename CompatibleArrayType>
Ed Tanousba9f9a62017-10-11 16:40:35 -07001196void from_json_array_impl(const BasicJsonType& j, CompatibleArrayType& arr, priority_tag<0> /*unused*/)
Ed Tanous3dac7492017-08-02 13:46:20 -07001197{
Ed Tanous3dac7492017-08-02 13:46:20 -07001198 using std::end;
1199
1200 std::transform(j.begin(), j.end(),
1201 std::inserter(arr, end(arr)), [](const BasicJsonType & i)
1202 {
1203 // get<BasicJsonType>() returns *this, this won't call a from_json
1204 // method when value_type is BasicJsonType
1205 return i.template get<typename CompatibleArrayType::value_type>();
1206 });
1207}
1208
1209template<typename BasicJsonType, typename CompatibleArrayType>
Ed Tanousba9f9a62017-10-11 16:40:35 -07001210auto from_json_array_impl(const BasicJsonType& j, CompatibleArrayType& arr, priority_tag<1> /*unused*/)
Ed Tanous3dac7492017-08-02 13:46:20 -07001211-> decltype(
1212 arr.reserve(std::declval<typename CompatibleArrayType::size_type>()),
1213 void())
1214{
Ed Tanous3dac7492017-08-02 13:46:20 -07001215 using std::end;
1216
1217 arr.reserve(j.size());
Ed Tanousba9f9a62017-10-11 16:40:35 -07001218 std::transform(j.begin(), j.end(),
1219 std::inserter(arr, end(arr)), [](const BasicJsonType & i)
Ed Tanous3dac7492017-08-02 13:46:20 -07001220 {
1221 // get<BasicJsonType>() returns *this, this won't call a from_json
1222 // method when value_type is BasicJsonType
1223 return i.template get<typename CompatibleArrayType::value_type>();
1224 });
1225}
1226
Ed Tanousba9f9a62017-10-11 16:40:35 -07001227template<typename BasicJsonType, typename T, std::size_t N>
1228void from_json_array_impl(const BasicJsonType& j, std::array<T, N>& arr, priority_tag<2> /*unused*/)
1229{
1230 for (std::size_t i = 0; i < N; ++i)
1231 {
1232 arr[i] = j.at(i).template get<T>();
1233 }
1234}
1235
Ed Tanous3dac7492017-08-02 13:46:20 -07001236template<typename BasicJsonType, typename CompatibleArrayType,
1237 enable_if_t<is_compatible_array_type<BasicJsonType, CompatibleArrayType>::value and
Ed Tanousba9f9a62017-10-11 16:40:35 -07001238 std::is_convertible<BasicJsonType, typename CompatibleArrayType::value_type>::value and
Ed Tanous3dac7492017-08-02 13:46:20 -07001239 not std::is_same<typename BasicJsonType::array_t, CompatibleArrayType>::value, int> = 0>
1240void from_json(const BasicJsonType& j, CompatibleArrayType& arr)
1241{
Ed Tanousba9f9a62017-10-11 16:40:35 -07001242 if (JSON_UNLIKELY(not j.is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -07001243 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07001244 JSON_THROW(type_error::create(302, "type must be array, but is " + std::string(j.type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07001245 }
1246
Ed Tanousba9f9a62017-10-11 16:40:35 -07001247 from_json_array_impl(j, arr, priority_tag<2> {});
Ed Tanous3dac7492017-08-02 13:46:20 -07001248}
1249
1250template<typename BasicJsonType, typename CompatibleObjectType,
1251 enable_if_t<is_compatible_object_type<BasicJsonType, CompatibleObjectType>::value, int> = 0>
1252void from_json(const BasicJsonType& j, CompatibleObjectType& obj)
1253{
Ed Tanousba9f9a62017-10-11 16:40:35 -07001254 if (JSON_UNLIKELY(not j.is_object()))
Ed Tanous3dac7492017-08-02 13:46:20 -07001255 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07001256 JSON_THROW(type_error::create(302, "type must be object, but is " + std::string(j.type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07001257 }
1258
1259 auto inner_object = j.template get_ptr<const typename BasicJsonType::object_t*>();
Ed Tanousba9f9a62017-10-11 16:40:35 -07001260 using value_type = typename CompatibleObjectType::value_type;
1261 std::transform(
1262 inner_object->begin(), inner_object->end(),
1263 std::inserter(obj, obj.begin()),
1264 [](typename BasicJsonType::object_t::value_type const & p)
1265 {
1266 return value_type(p.first, p.second.template get<typename CompatibleObjectType::mapped_type>());
1267 });
Ed Tanous3dac7492017-08-02 13:46:20 -07001268}
1269
1270// overload for arithmetic types, not chosen for basic_json template arguments
1271// (BooleanType, etc..); note: Is it really necessary to provide explicit
1272// overloads for boolean_t etc. in case of a custom BooleanType which is not
1273// an arithmetic type?
1274template<typename BasicJsonType, typename ArithmeticType,
1275 enable_if_t <
1276 std::is_arithmetic<ArithmeticType>::value and
1277 not std::is_same<ArithmeticType, typename BasicJsonType::number_unsigned_t>::value and
1278 not std::is_same<ArithmeticType, typename BasicJsonType::number_integer_t>::value and
1279 not std::is_same<ArithmeticType, typename BasicJsonType::number_float_t>::value and
1280 not std::is_same<ArithmeticType, typename BasicJsonType::boolean_t>::value,
1281 int> = 0>
1282void from_json(const BasicJsonType& j, ArithmeticType& val)
1283{
1284 switch (static_cast<value_t>(j))
1285 {
1286 case value_t::number_unsigned:
1287 {
1288 val = static_cast<ArithmeticType>(*j.template get_ptr<const typename BasicJsonType::number_unsigned_t*>());
1289 break;
1290 }
1291 case value_t::number_integer:
1292 {
1293 val = static_cast<ArithmeticType>(*j.template get_ptr<const typename BasicJsonType::number_integer_t*>());
1294 break;
1295 }
1296 case value_t::number_float:
1297 {
1298 val = static_cast<ArithmeticType>(*j.template get_ptr<const typename BasicJsonType::number_float_t*>());
1299 break;
1300 }
1301 case value_t::boolean:
1302 {
1303 val = static_cast<ArithmeticType>(*j.template get_ptr<const typename BasicJsonType::boolean_t*>());
1304 break;
1305 }
Ed Tanousba9f9a62017-10-11 16:40:35 -07001306
Ed Tanous3dac7492017-08-02 13:46:20 -07001307 default:
Ed Tanousba9f9a62017-10-11 16:40:35 -07001308 JSON_THROW(type_error::create(302, "type must be number, but is " + std::string(j.type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07001309 }
1310}
1311
Ed Tanousba9f9a62017-10-11 16:40:35 -07001312template<typename BasicJsonType, typename A1, typename A2>
1313void from_json(const BasicJsonType& j, std::pair<A1, A2>& p)
1314{
1315 p = {j.at(0).template get<A1>(), j.at(1).template get<A2>()};
1316}
1317
1318template<typename BasicJsonType, typename Tuple, std::size_t... Idx>
1319void from_json_tuple_impl(const BasicJsonType& j, Tuple& t, index_sequence<Idx...>)
1320{
1321 t = std::make_tuple(j.at(Idx).template get<typename std::tuple_element<Idx, Tuple>::type>()...);
1322}
1323
1324template<typename BasicJsonType, typename... Args>
1325void from_json(const BasicJsonType& j, std::tuple<Args...>& t)
1326{
1327 from_json_tuple_impl(j, t, index_sequence_for<Args...> {});
1328}
1329
Ed Tanous3dac7492017-08-02 13:46:20 -07001330struct to_json_fn
1331{
1332 private:
1333 template<typename BasicJsonType, typename T>
Ed Tanousba9f9a62017-10-11 16:40:35 -07001334 auto call(BasicJsonType& j, T&& val, priority_tag<1> /*unused*/) const noexcept(noexcept(to_json(j, std::forward<T>(val))))
Ed Tanous3dac7492017-08-02 13:46:20 -07001335 -> decltype(to_json(j, std::forward<T>(val)), void())
1336 {
1337 return to_json(j, std::forward<T>(val));
1338 }
1339
1340 template<typename BasicJsonType, typename T>
Ed Tanousba9f9a62017-10-11 16:40:35 -07001341 void call(BasicJsonType& /*unused*/, T&& /*unused*/, priority_tag<0> /*unused*/) const noexcept
Ed Tanous3dac7492017-08-02 13:46:20 -07001342 {
1343 static_assert(sizeof(BasicJsonType) == 0,
1344 "could not find to_json() method in T's namespace");
1345 }
1346
1347 public:
1348 template<typename BasicJsonType, typename T>
1349 void operator()(BasicJsonType& j, T&& val) const
1350 noexcept(noexcept(std::declval<to_json_fn>().call(j, std::forward<T>(val), priority_tag<1> {})))
1351 {
1352 return call(j, std::forward<T>(val), priority_tag<1> {});
1353 }
1354};
1355
1356struct from_json_fn
1357{
1358 private:
1359 template<typename BasicJsonType, typename T>
Ed Tanousba9f9a62017-10-11 16:40:35 -07001360 auto call(const BasicJsonType& j, T& val, priority_tag<1> /*unused*/) const
Ed Tanous3dac7492017-08-02 13:46:20 -07001361 noexcept(noexcept(from_json(j, val)))
1362 -> decltype(from_json(j, val), void())
1363 {
1364 return from_json(j, val);
1365 }
1366
1367 template<typename BasicJsonType, typename T>
Ed Tanousba9f9a62017-10-11 16:40:35 -07001368 void call(const BasicJsonType& /*unused*/, T& /*unused*/, priority_tag<0> /*unused*/) const noexcept
Ed Tanous3dac7492017-08-02 13:46:20 -07001369 {
1370 static_assert(sizeof(BasicJsonType) == 0,
1371 "could not find from_json() method in T's namespace");
1372 }
1373
1374 public:
1375 template<typename BasicJsonType, typename T>
1376 void operator()(const BasicJsonType& j, T& val) const
1377 noexcept(noexcept(std::declval<from_json_fn>().call(j, val, priority_tag<1> {})))
1378 {
1379 return call(j, val, priority_tag<1> {});
1380 }
1381};
1382
1383// taken from ranges-v3
1384template<typename T>
1385struct static_const
1386{
1387 static constexpr T value{};
1388};
1389
1390template<typename T>
1391constexpr T static_const<T>::value;
Ed Tanous3dac7492017-08-02 13:46:20 -07001392
Ed Tanousba9f9a62017-10-11 16:40:35 -07001393////////////////////
1394// input adapters //
1395////////////////////
1396
1397/// abstract input adapter interface
1398struct input_adapter_protocol
1399{
1400 virtual int get_character() = 0;
1401 virtual std::string read(std::size_t offset, std::size_t length) = 0;
1402 virtual ~input_adapter_protocol() = default;
1403};
1404
1405/// a type to simplify interfaces
1406using input_adapter_t = std::shared_ptr<input_adapter_protocol>;
1407
1408/// input adapter for cached stream input
1409template<std::size_t BufferSize>
1410class cached_input_stream_adapter : public input_adapter_protocol
1411{
1412 public:
1413 explicit cached_input_stream_adapter(std::istream& i)
1414 : is(i), start_position(is.tellg())
1415 {
1416 fill_buffer();
1417
1418 // skip byte order mark
1419 if (fill_size >= 3 and buffer[0] == '\xEF' and buffer[1] == '\xBB' and buffer[2] == '\xBF')
1420 {
1421 buffer_pos += 3;
1422 processed_chars += 3;
1423 }
1424 }
1425
1426 ~cached_input_stream_adapter() override
1427 {
1428 // clear stream flags
1429 is.clear();
1430 // We initially read a lot of characters into the buffer, and we may
1431 // not have processed all of them. Therefore, we need to "rewind" the
1432 // stream after the last processed char.
1433 is.seekg(start_position);
1434 is.ignore(static_cast<std::streamsize>(processed_chars));
1435 // clear stream flags
1436 is.clear();
1437 }
1438
1439 int get_character() override
1440 {
1441 // check if refilling is necessary and possible
1442 if (buffer_pos == fill_size and not eof)
1443 {
1444 fill_buffer();
1445
1446 // check and remember that filling did not yield new input
1447 if (fill_size == 0)
1448 {
1449 eof = true;
1450 return std::char_traits<char>::eof();
1451 }
1452
1453 // the buffer is ready
1454 buffer_pos = 0;
1455 }
1456
1457 ++processed_chars;
1458 assert(buffer_pos < buffer.size());
1459 return buffer[buffer_pos++] & 0xFF;
1460 }
1461
1462 std::string read(std::size_t offset, std::size_t length) override
1463 {
1464 // create buffer
1465 std::string result(length, '\0');
1466
1467 // save stream position
1468 const auto current_pos = is.tellg();
1469 // save stream flags
1470 const auto flags = is.rdstate();
1471
1472 // clear stream flags
1473 is.clear();
1474 // set stream position
1475 is.seekg(static_cast<std::streamoff>(offset));
1476 // read bytes
1477 is.read(&result[0], static_cast<std::streamsize>(length));
1478
1479 // reset stream position
1480 is.seekg(current_pos);
1481 // reset stream flags
1482 is.setstate(flags);
1483
1484 return result;
1485 }
1486
1487 private:
1488 void fill_buffer()
1489 {
1490 // fill
1491 is.read(buffer.data(), static_cast<std::streamsize>(buffer.size()));
1492 // store number of bytes in the buffer
1493 fill_size = static_cast<size_t>(is.gcount());
1494 }
1495
1496 /// the associated input stream
1497 std::istream& is;
1498
1499 /// chars returned via get_character()
1500 std::size_t processed_chars = 0;
1501 /// chars processed in the current buffer
1502 std::size_t buffer_pos = 0;
1503
1504 /// whether stream reached eof
1505 bool eof = false;
1506 /// how many chars have been copied to the buffer by last (re)fill
1507 std::size_t fill_size = 0;
1508
1509 /// position of the stream when we started
1510 const std::streampos start_position;
1511
1512 /// internal buffer
1513 std::array<char, BufferSize> buffer{{}};
1514};
1515
1516/// input adapter for buffer input
1517class input_buffer_adapter : public input_adapter_protocol
1518{
1519 public:
1520 input_buffer_adapter(const char* b, const std::size_t l)
1521 : cursor(b), limit(b + l), start(b)
1522 {
1523 // skip byte order mark
1524 if (l >= 3 and b[0] == '\xEF' and b[1] == '\xBB' and b[2] == '\xBF')
1525 {
1526 cursor += 3;
1527 }
1528 }
1529
1530 // delete because of pointer members
1531 input_buffer_adapter(const input_buffer_adapter&) = delete;
1532 input_buffer_adapter& operator=(input_buffer_adapter&) = delete;
1533
1534 int get_character() noexcept override
1535 {
1536 if (JSON_LIKELY(cursor < limit))
1537 {
1538 return *(cursor++) & 0xFF;
1539 }
1540
1541 return std::char_traits<char>::eof();
1542 }
1543
1544 std::string read(std::size_t offset, std::size_t length) override
1545 {
1546 // avoid reading too many characters
1547 const auto max_length = static_cast<size_t>(limit - start);
1548 return std::string(start + offset, (std::min)(length, max_length - offset));
1549 }
1550
1551 private:
1552 /// pointer to the current character
1553 const char* cursor;
1554 /// pointer past the last character
1555 const char* limit;
1556 /// pointer to the first character
1557 const char* start;
1558};
1559
1560class input_adapter
1561{
1562 public:
1563 // native support
1564
1565 /// input adapter for input stream
1566 input_adapter(std::istream& i)
1567 : ia(std::make_shared<cached_input_stream_adapter<16384>>(i)) {}
1568
1569 /// input adapter for input stream
1570 input_adapter(std::istream&& i)
1571 : ia(std::make_shared<cached_input_stream_adapter<16384>>(i)) {}
1572
1573 /// input adapter for buffer
1574 template<typename CharT,
1575 typename std::enable_if<
1576 std::is_pointer<CharT>::value and
1577 std::is_integral<
1578 typename std::remove_pointer<CharT>::type>::value and
1579 sizeof(typename std::remove_pointer<CharT>::type) == 1,
1580 int>::type = 0>
1581 input_adapter(CharT b, std::size_t l)
1582 : ia(std::make_shared<input_buffer_adapter>(reinterpret_cast<const char*>(b), l)) {}
1583
1584 // derived support
1585
1586 /// input adapter for string literal
1587 template<typename CharT,
1588 typename std::enable_if<
1589 std::is_pointer<CharT>::value and
1590 std::is_integral<
1591 typename std::remove_pointer<CharT>::type>::value and
1592 sizeof(typename std::remove_pointer<CharT>::type) == 1,
1593 int>::type = 0>
1594 input_adapter(CharT b)
1595 : input_adapter(reinterpret_cast<const char*>(b),
1596 std::strlen(reinterpret_cast<const char*>(b))) {}
1597
1598 /// input adapter for iterator range with contiguous storage
1599 template<class IteratorType,
1600 typename std::enable_if<
1601 std::is_same<typename std::iterator_traits<IteratorType>::iterator_category,
1602 std::random_access_iterator_tag>::value,
1603 int>::type = 0>
1604 input_adapter(IteratorType first, IteratorType last)
1605 {
1606 // assertion to check that the iterator range is indeed contiguous,
1607 // see http://stackoverflow.com/a/35008842/266378 for more discussion
1608 assert(std::accumulate(
1609 first, last, std::pair<bool, int>(true, 0),
1610 [&first](std::pair<bool, int> res, decltype(*first) val)
1611 {
1612 res.first &= (val == *(std::next(std::addressof(*first), res.second++)));
1613 return res;
1614 }).first);
1615
1616 // assertion to check that each element is 1 byte long
1617 static_assert(
1618 sizeof(typename std::iterator_traits<IteratorType>::value_type) == 1,
1619 "each element in the iterator range must have the size of 1 byte");
1620
1621 const auto len = static_cast<size_t>(std::distance(first, last));
1622 if (JSON_LIKELY(len > 0))
1623 {
1624 // there is at least one element: use the address of first
1625 ia = std::make_shared<input_buffer_adapter>(reinterpret_cast<const char*>(&(*first)), len);
1626 }
1627 else
1628 {
1629 // the address of first cannot be used: use nullptr
1630 ia = std::make_shared<input_buffer_adapter>(nullptr, len);
1631 }
1632 }
1633
1634 /// input adapter for array
1635 template<class T, std::size_t N>
1636 input_adapter(T (&array)[N])
1637 : input_adapter(std::begin(array), std::end(array)) {}
1638
1639 /// input adapter for contiguous container
1640 template <
1641 class ContiguousContainer,
1642 typename std::enable_if <
1643 not std::is_pointer<ContiguousContainer>::value and
1644 std::is_base_of<std::random_access_iterator_tag,
1645 typename std::iterator_traits<decltype(std::begin(std::declval<ContiguousContainer const>()))>::iterator_category>::value,
1646 int >::type = 0 >
1647 input_adapter(const ContiguousContainer& c)
1648 : input_adapter(std::begin(c), std::end(c)) {}
1649
1650 operator input_adapter_t()
1651 {
1652 return ia;
1653 }
1654
1655 private:
1656 /// the actual adapter
1657 input_adapter_t ia = nullptr;
1658};
1659
1660//////////////////////
1661// lexer and parser //
1662//////////////////////
1663
1664/*!
1665@brief lexical analysis
1666
1667This class organizes the lexical analysis during JSON deserialization.
1668*/
1669template<typename BasicJsonType>
1670class lexer
1671{
1672 using number_integer_t = typename BasicJsonType::number_integer_t;
1673 using number_unsigned_t = typename BasicJsonType::number_unsigned_t;
1674 using number_float_t = typename BasicJsonType::number_float_t;
1675
1676 public:
1677 /// token types for the parser
1678 enum class token_type
1679 {
1680 uninitialized, ///< indicating the scanner is uninitialized
1681 literal_true, ///< the `true` literal
1682 literal_false, ///< the `false` literal
1683 literal_null, ///< the `null` literal
1684 value_string, ///< a string -- use get_string() for actual value
1685 value_unsigned, ///< an unsigned integer -- use get_number_unsigned() for actual value
1686 value_integer, ///< a signed integer -- use get_number_integer() for actual value
1687 value_float, ///< an floating point number -- use get_number_float() for actual value
1688 begin_array, ///< the character for array begin `[`
1689 begin_object, ///< the character for object begin `{`
1690 end_array, ///< the character for array end `]`
1691 end_object, ///< the character for object end `}`
1692 name_separator, ///< the name separator `:`
1693 value_separator, ///< the value separator `,`
1694 parse_error, ///< indicating a parse error
1695 end_of_input, ///< indicating the end of the input buffer
1696 literal_or_value ///< a literal or the begin of a value (only for diagnostics)
1697 };
1698
1699 /// return name of values of type token_type (only used for errors)
1700 static const char* token_type_name(const token_type t) noexcept
1701 {
1702 switch (t)
1703 {
1704 case token_type::uninitialized:
1705 return "<uninitialized>";
1706 case token_type::literal_true:
1707 return "true literal";
1708 case token_type::literal_false:
1709 return "false literal";
1710 case token_type::literal_null:
1711 return "null literal";
1712 case token_type::value_string:
1713 return "string literal";
1714 case lexer::token_type::value_unsigned:
1715 case lexer::token_type::value_integer:
1716 case lexer::token_type::value_float:
1717 return "number literal";
1718 case token_type::begin_array:
1719 return "'['";
1720 case token_type::begin_object:
1721 return "'{'";
1722 case token_type::end_array:
1723 return "']'";
1724 case token_type::end_object:
1725 return "'}'";
1726 case token_type::name_separator:
1727 return "':'";
1728 case token_type::value_separator:
1729 return "','";
1730 case token_type::parse_error:
1731 return "<parse error>";
1732 case token_type::end_of_input:
1733 return "end of input";
1734 case token_type::literal_or_value:
1735 return "'[', '{', or a literal";
1736 default: // catch non-enum values
1737 return "unknown token"; // LCOV_EXCL_LINE
1738 }
1739 }
1740
1741 explicit lexer(detail::input_adapter_t adapter)
1742 : ia(std::move(adapter)), decimal_point_char(get_decimal_point()) {}
1743
1744 // delete because of pointer members
1745 lexer(const lexer&) = delete;
1746 lexer& operator=(lexer&) = delete;
1747
1748 private:
1749 /////////////////////
1750 // locales
1751 /////////////////////
1752
1753 /// return the locale-dependent decimal point
1754 static char get_decimal_point() noexcept
1755 {
1756 const auto loc = localeconv();
1757 assert(loc != nullptr);
1758 return (loc->decimal_point == nullptr) ? '.' : loc->decimal_point[0];
1759 }
1760
1761 /////////////////////
1762 // scan functions
1763 /////////////////////
1764
1765 /*!
1766 @brief get codepoint from 4 hex characters following `\u`
1767
1768 For input "\u c1 c2 c3 c4" the codepoint is:
1769 (c1 * 0x1000) + (c2 * 0x0100) + (c3 * 0x0010) + c4
1770 = (c1 << 12) + (c2 << 8) + (c3 << 4) + (c4 << 0)
1771
1772 Furthermore, the possible characters '0'..'9', 'A'..'F', and 'a'..'f'
1773 must be converted to the integers 0x0..0x9, 0xA..0xF, 0xA..0xF, resp. The
1774 conversion is done by subtracting the offset (0x30, 0x37, and 0x57)
1775 between the ASCII value of the character and the desired integer value.
1776
1777 @return codepoint (0x0000..0xFFFF) or -1 in case of an error (e.g. EOF or
1778 non-hex character)
1779 */
1780 int get_codepoint()
1781 {
1782 // this function only makes sense after reading `\u`
1783 assert(current == 'u');
1784 int codepoint = 0;
1785
1786 const auto factors = { 12, 8, 4, 0 };
1787 for (const auto factor : factors)
1788 {
1789 get();
1790
1791 if (current >= '0' and current <= '9')
1792 {
1793 codepoint += ((current - 0x30) << factor);
1794 }
1795 else if (current >= 'A' and current <= 'F')
1796 {
1797 codepoint += ((current - 0x37) << factor);
1798 }
1799 else if (current >= 'a' and current <= 'f')
1800 {
1801 codepoint += ((current - 0x57) << factor);
1802 }
1803 else
1804 {
1805 return -1;
1806 }
1807 }
1808
1809 assert(0x0000 <= codepoint and codepoint <= 0xFFFF);
1810 return codepoint;
1811 }
1812
1813 /*!
1814 @brief check if the next byte(s) are inside a given range
1815
1816 Adds the current byte and, for each passed range, reads a new byte and
1817 checks if it is inside the range. If a violation was detected, set up an
1818 error message and return false. Otherwise, return true.
1819
1820 @return true if and only if no range violation was detected
1821 */
1822 bool next_byte_in_range(std::initializer_list<int> ranges)
1823 {
1824 assert(ranges.size() == 2 or ranges.size() == 4 or ranges.size() == 6);
1825 add(current);
1826
1827 for (auto range = ranges.begin(); range != ranges.end(); ++range)
1828 {
1829 get();
1830 if (JSON_LIKELY(*range <= current and current <= *(++range)))
1831 {
1832 add(current);
1833 }
1834 else
1835 {
1836 error_message = "invalid string: ill-formed UTF-8 byte";
1837 return false;
1838 }
1839 }
1840
1841 return true;
1842 }
1843
1844 /*!
1845 @brief scan a string literal
1846
1847 This function scans a string according to Sect. 7 of RFC 7159. While
1848 scanning, bytes are escaped and copied into buffer yytext. Then the
1849 function returns successfully, yytext is null-terminated and yylen
1850 contains the number of bytes in the string.
1851
1852 @return token_type::value_string if string could be successfully scanned,
1853 token_type::parse_error otherwise
1854
1855 @note In case of errors, variable error_message contains a textual
1856 description.
1857 */
1858 token_type scan_string()
1859 {
1860 // reset yytext (ignore opening quote)
1861 reset();
1862
1863 // we entered the function by reading an open quote
1864 assert(current == '\"');
1865
1866 while (true)
1867 {
1868 // get next character
1869 switch (get())
1870 {
1871 // end of file while parsing string
1872 case std::char_traits<char>::eof():
1873 {
1874 error_message = "invalid string: missing closing quote";
1875 return token_type::parse_error;
1876 }
1877
1878 // closing quote
1879 case '\"':
1880 {
1881 // terminate yytext
1882 add('\0');
1883 --yylen;
1884 return token_type::value_string;
1885 }
1886
1887 // escapes
1888 case '\\':
1889 {
1890 switch (get())
1891 {
1892 // quotation mark
1893 case '\"':
1894 add('\"');
1895 break;
1896 // reverse solidus
1897 case '\\':
1898 add('\\');
1899 break;
1900 // solidus
1901 case '/':
1902 add('/');
1903 break;
1904 // backspace
1905 case 'b':
1906 add('\b');
1907 break;
1908 // form feed
1909 case 'f':
1910 add('\f');
1911 break;
1912 // line feed
1913 case 'n':
1914 add('\n');
1915 break;
1916 // carriage return
1917 case 'r':
1918 add('\r');
1919 break;
1920 // tab
1921 case 't':
1922 add('\t');
1923 break;
1924
1925 // unicode escapes
1926 case 'u':
1927 {
1928 int codepoint;
1929 const int codepoint1 = get_codepoint();
1930
1931 if (JSON_UNLIKELY(codepoint1 == -1))
1932 {
1933 error_message = "invalid string: '\\u' must be followed by 4 hex digits";
1934 return token_type::parse_error;
1935 }
1936
1937 // check if code point is a high surrogate
1938 if (0xD800 <= codepoint1 and codepoint1 <= 0xDBFF)
1939 {
1940 // expect next \uxxxx entry
1941 if (JSON_LIKELY(get() == '\\' and get() == 'u'))
1942 {
1943 const int codepoint2 = get_codepoint();
1944
1945 if (JSON_UNLIKELY(codepoint2 == -1))
1946 {
1947 error_message = "invalid string: '\\u' must be followed by 4 hex digits";
1948 return token_type::parse_error;
1949 }
1950
1951 // check if codepoint2 is a low surrogate
1952 if (JSON_LIKELY(0xDC00 <= codepoint2 and codepoint2 <= 0xDFFF))
1953 {
1954 codepoint =
1955 // high surrogate occupies the most significant 22 bits
1956 (codepoint1 << 10)
1957 // low surrogate occupies the least significant 15 bits
1958 + codepoint2
1959 // there is still the 0xD800, 0xDC00 and 0x10000 noise
1960 // in the result so we have to subtract with:
1961 // (0xD800 << 10) + DC00 - 0x10000 = 0x35FDC00
1962 - 0x35FDC00;
1963 }
1964 else
1965 {
1966 error_message = "invalid string: surrogate U+DC00..U+DFFF must be followed by U+DC00..U+DFFF";
1967 return token_type::parse_error;
1968 }
1969 }
1970 else
1971 {
1972 error_message = "invalid string: surrogate U+DC00..U+DFFF must be followed by U+DC00..U+DFFF";
1973 return token_type::parse_error;
1974 }
1975 }
1976 else
1977 {
1978 if (JSON_UNLIKELY(0xDC00 <= codepoint1 and codepoint1 <= 0xDFFF))
1979 {
1980 error_message = "invalid string: surrogate U+DC00..U+DFFF must follow U+D800..U+DBFF";
1981 return token_type::parse_error;
1982 }
1983
1984 // only work with first code point
1985 codepoint = codepoint1;
1986 }
1987
1988 // result of the above calculation yields a proper codepoint
1989 assert(0x00 <= codepoint and codepoint <= 0x10FFFF);
1990
1991 // translate code point to bytes
1992 if (codepoint < 0x80)
1993 {
1994 // 1-byte characters: 0xxxxxxx (ASCII)
1995 add(codepoint);
1996 }
1997 else if (codepoint <= 0x7ff)
1998 {
1999 // 2-byte characters: 110xxxxx 10xxxxxx
2000 add(0xC0 | (codepoint >> 6));
2001 add(0x80 | (codepoint & 0x3F));
2002 }
2003 else if (codepoint <= 0xffff)
2004 {
2005 // 3-byte characters: 1110xxxx 10xxxxxx 10xxxxxx
2006 add(0xE0 | (codepoint >> 12));
2007 add(0x80 | ((codepoint >> 6) & 0x3F));
2008 add(0x80 | (codepoint & 0x3F));
2009 }
2010 else
2011 {
2012 // 4-byte characters: 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
2013 add(0xF0 | (codepoint >> 18));
2014 add(0x80 | ((codepoint >> 12) & 0x3F));
2015 add(0x80 | ((codepoint >> 6) & 0x3F));
2016 add(0x80 | (codepoint & 0x3F));
2017 }
2018
2019 break;
2020 }
2021
2022 // other characters after escape
2023 default:
2024 error_message = "invalid string: forbidden character after backslash";
2025 return token_type::parse_error;
2026 }
2027
2028 break;
2029 }
2030
2031 // invalid control characters
2032 case 0x00:
2033 case 0x01:
2034 case 0x02:
2035 case 0x03:
2036 case 0x04:
2037 case 0x05:
2038 case 0x06:
2039 case 0x07:
2040 case 0x08:
2041 case 0x09:
2042 case 0x0a:
2043 case 0x0b:
2044 case 0x0c:
2045 case 0x0d:
2046 case 0x0e:
2047 case 0x0f:
2048 case 0x10:
2049 case 0x11:
2050 case 0x12:
2051 case 0x13:
2052 case 0x14:
2053 case 0x15:
2054 case 0x16:
2055 case 0x17:
2056 case 0x18:
2057 case 0x19:
2058 case 0x1a:
2059 case 0x1b:
2060 case 0x1c:
2061 case 0x1d:
2062 case 0x1e:
2063 case 0x1f:
2064 {
2065 error_message = "invalid string: control character must be escaped";
2066 return token_type::parse_error;
2067 }
2068
2069 // U+0020..U+007F (except U+0022 (quote) and U+005C (backspace))
2070 case 0x20:
2071 case 0x21:
2072 case 0x23:
2073 case 0x24:
2074 case 0x25:
2075 case 0x26:
2076 case 0x27:
2077 case 0x28:
2078 case 0x29:
2079 case 0x2a:
2080 case 0x2b:
2081 case 0x2c:
2082 case 0x2d:
2083 case 0x2e:
2084 case 0x2f:
2085 case 0x30:
2086 case 0x31:
2087 case 0x32:
2088 case 0x33:
2089 case 0x34:
2090 case 0x35:
2091 case 0x36:
2092 case 0x37:
2093 case 0x38:
2094 case 0x39:
2095 case 0x3a:
2096 case 0x3b:
2097 case 0x3c:
2098 case 0x3d:
2099 case 0x3e:
2100 case 0x3f:
2101 case 0x40:
2102 case 0x41:
2103 case 0x42:
2104 case 0x43:
2105 case 0x44:
2106 case 0x45:
2107 case 0x46:
2108 case 0x47:
2109 case 0x48:
2110 case 0x49:
2111 case 0x4a:
2112 case 0x4b:
2113 case 0x4c:
2114 case 0x4d:
2115 case 0x4e:
2116 case 0x4f:
2117 case 0x50:
2118 case 0x51:
2119 case 0x52:
2120 case 0x53:
2121 case 0x54:
2122 case 0x55:
2123 case 0x56:
2124 case 0x57:
2125 case 0x58:
2126 case 0x59:
2127 case 0x5a:
2128 case 0x5b:
2129 case 0x5d:
2130 case 0x5e:
2131 case 0x5f:
2132 case 0x60:
2133 case 0x61:
2134 case 0x62:
2135 case 0x63:
2136 case 0x64:
2137 case 0x65:
2138 case 0x66:
2139 case 0x67:
2140 case 0x68:
2141 case 0x69:
2142 case 0x6a:
2143 case 0x6b:
2144 case 0x6c:
2145 case 0x6d:
2146 case 0x6e:
2147 case 0x6f:
2148 case 0x70:
2149 case 0x71:
2150 case 0x72:
2151 case 0x73:
2152 case 0x74:
2153 case 0x75:
2154 case 0x76:
2155 case 0x77:
2156 case 0x78:
2157 case 0x79:
2158 case 0x7a:
2159 case 0x7b:
2160 case 0x7c:
2161 case 0x7d:
2162 case 0x7e:
2163 case 0x7f:
2164 {
2165 add(current);
2166 break;
2167 }
2168
2169 // U+0080..U+07FF: bytes C2..DF 80..BF
2170 case 0xc2:
2171 case 0xc3:
2172 case 0xc4:
2173 case 0xc5:
2174 case 0xc6:
2175 case 0xc7:
2176 case 0xc8:
2177 case 0xc9:
2178 case 0xca:
2179 case 0xcb:
2180 case 0xcc:
2181 case 0xcd:
2182 case 0xce:
2183 case 0xcf:
2184 case 0xd0:
2185 case 0xd1:
2186 case 0xd2:
2187 case 0xd3:
2188 case 0xd4:
2189 case 0xd5:
2190 case 0xd6:
2191 case 0xd7:
2192 case 0xd8:
2193 case 0xd9:
2194 case 0xda:
2195 case 0xdb:
2196 case 0xdc:
2197 case 0xdd:
2198 case 0xde:
2199 case 0xdf:
2200 {
2201 if (JSON_UNLIKELY(not next_byte_in_range({0x80, 0xBF})))
2202 {
2203 return token_type::parse_error;
2204 }
2205 break;
2206 }
2207
2208 // U+0800..U+0FFF: bytes E0 A0..BF 80..BF
2209 case 0xe0:
2210 {
2211 if (JSON_UNLIKELY(not (next_byte_in_range({0xA0, 0xBF, 0x80, 0xBF}))))
2212 {
2213 return token_type::parse_error;
2214 }
2215 break;
2216 }
2217
2218 // U+1000..U+CFFF: bytes E1..EC 80..BF 80..BF
2219 // U+E000..U+FFFF: bytes EE..EF 80..BF 80..BF
2220 case 0xe1:
2221 case 0xe2:
2222 case 0xe3:
2223 case 0xe4:
2224 case 0xe5:
2225 case 0xe6:
2226 case 0xe7:
2227 case 0xe8:
2228 case 0xe9:
2229 case 0xea:
2230 case 0xeb:
2231 case 0xec:
2232 case 0xee:
2233 case 0xef:
2234 {
2235 if (JSON_UNLIKELY(not (next_byte_in_range({0x80, 0xBF, 0x80, 0xBF}))))
2236 {
2237 return token_type::parse_error;
2238 }
2239 break;
2240 }
2241
2242 // U+D000..U+D7FF: bytes ED 80..9F 80..BF
2243 case 0xed:
2244 {
2245 if (JSON_UNLIKELY(not (next_byte_in_range({0x80, 0x9F, 0x80, 0xBF}))))
2246 {
2247 return token_type::parse_error;
2248 }
2249 break;
2250 }
2251
2252 // U+10000..U+3FFFF F0 90..BF 80..BF 80..BF
2253 case 0xf0:
2254 {
2255 if (JSON_UNLIKELY(not (next_byte_in_range({0x90, 0xBF, 0x80, 0xBF, 0x80, 0xBF}))))
2256 {
2257 return token_type::parse_error;
2258 }
2259 break;
2260 }
2261
2262 // U+40000..U+FFFFF F1..F3 80..BF 80..BF 80..BF
2263 case 0xf1:
2264 case 0xf2:
2265 case 0xf3:
2266 {
2267 if (JSON_UNLIKELY(not (next_byte_in_range({0x80, 0xBF, 0x80, 0xBF, 0x80, 0xBF}))))
2268 {
2269 return token_type::parse_error;
2270 }
2271 break;
2272 }
2273
2274 // U+100000..U+10FFFF F4 80..8F 80..BF 80..BF
2275 case 0xf4:
2276 {
2277 if (JSON_UNLIKELY(not (next_byte_in_range({0x80, 0x8F, 0x80, 0xBF, 0x80, 0xBF}))))
2278 {
2279 return token_type::parse_error;
2280 }
2281 break;
2282 }
2283
2284 // remaining bytes (80..C1 and F5..FF) are ill-formed
2285 default:
2286 {
2287 error_message = "invalid string: ill-formed UTF-8 byte";
2288 return token_type::parse_error;
2289 }
2290 }
2291 }
2292 }
2293
2294 static void strtof(float& f, const char* str, char** endptr) noexcept
2295 {
2296 f = std::strtof(str, endptr);
2297 }
2298
2299 static void strtof(double& f, const char* str, char** endptr) noexcept
2300 {
2301 f = std::strtod(str, endptr);
2302 }
2303
2304 static void strtof(long double& f, const char* str, char** endptr) noexcept
2305 {
2306 f = std::strtold(str, endptr);
2307 }
2308
2309 /*!
2310 @brief scan a number literal
2311
2312 This function scans a string according to Sect. 6 of RFC 7159.
2313
2314 The function is realized with a deterministic finite state machine derived
2315 from the grammar described in RFC 7159. Starting in state "init", the
2316 input is read and used to determined the next state. Only state "done"
2317 accepts the number. State "error" is a trap state to model errors. In the
2318 table below, "anything" means any character but the ones listed before.
2319
2320 state | 0 | 1-9 | e E | + | - | . | anything
2321 ---------|----------|----------|----------|---------|---------|----------|-----------
2322 init | zero | any1 | [error] | [error] | minus | [error] | [error]
2323 minus | zero | any1 | [error] | [error] | [error] | [error] | [error]
2324 zero | done | done | exponent | done | done | decimal1 | done
2325 any1 | any1 | any1 | exponent | done | done | decimal1 | done
2326 decimal1 | decimal2 | [error] | [error] | [error] | [error] | [error] | [error]
2327 decimal2 | decimal2 | decimal2 | exponent | done | done | done | done
2328 exponent | any2 | any2 | [error] | sign | sign | [error] | [error]
2329 sign | any2 | any2 | [error] | [error] | [error] | [error] | [error]
2330 any2 | any2 | any2 | done | done | done | done | done
2331
2332 The state machine is realized with one label per state (prefixed with
2333 "scan_number_") and `goto` statements between them. The state machine
2334 contains cycles, but any cycle can be left when EOF is read. Therefore,
2335 the function is guaranteed to terminate.
2336
2337 During scanning, the read bytes are stored in yytext. This string is
2338 then converted to a signed integer, an unsigned integer, or a
2339 floating-point number.
2340
2341 @return token_type::value_unsigned, token_type::value_integer, or
2342 token_type::value_float if number could be successfully scanned,
2343 token_type::parse_error otherwise
2344
2345 @note The scanner is independent of the current locale. Internally, the
2346 locale's decimal point is used instead of `.` to work with the
2347 locale-dependent converters.
2348 */
2349 token_type scan_number()
2350 {
2351 // reset yytext to store the number's bytes
2352 reset();
2353
2354 // the type of the parsed number; initially set to unsigned; will be
2355 // changed if minus sign, decimal point or exponent is read
2356 token_type number_type = token_type::value_unsigned;
2357
2358 // state (init): we just found out we need to scan a number
2359 switch (current)
2360 {
2361 case '-':
2362 {
2363 add(current);
2364 goto scan_number_minus;
2365 }
2366
2367 case '0':
2368 {
2369 add(current);
2370 goto scan_number_zero;
2371 }
2372
2373 case '1':
2374 case '2':
2375 case '3':
2376 case '4':
2377 case '5':
2378 case '6':
2379 case '7':
2380 case '8':
2381 case '9':
2382 {
2383 add(current);
2384 goto scan_number_any1;
2385 }
2386
2387 default:
2388 {
2389 // all other characters are rejected outside scan_number()
2390 assert(false); // LCOV_EXCL_LINE
2391 }
2392 }
2393
2394scan_number_minus:
2395 // state: we just parsed a leading minus sign
2396 number_type = token_type::value_integer;
2397 switch (get())
2398 {
2399 case '0':
2400 {
2401 add(current);
2402 goto scan_number_zero;
2403 }
2404
2405 case '1':
2406 case '2':
2407 case '3':
2408 case '4':
2409 case '5':
2410 case '6':
2411 case '7':
2412 case '8':
2413 case '9':
2414 {
2415 add(current);
2416 goto scan_number_any1;
2417 }
2418
2419 default:
2420 {
2421 error_message = "invalid number; expected digit after '-'";
2422 return token_type::parse_error;
2423 }
2424 }
2425
2426scan_number_zero:
2427 // state: we just parse a zero (maybe with a leading minus sign)
2428 switch (get())
2429 {
2430 case '.':
2431 {
2432 add(decimal_point_char);
2433 goto scan_number_decimal1;
2434 }
2435
2436 case 'e':
2437 case 'E':
2438 {
2439 add(current);
2440 goto scan_number_exponent;
2441 }
2442
2443 default:
2444 goto scan_number_done;
2445 }
2446
2447scan_number_any1:
2448 // state: we just parsed a number 0-9 (maybe with a leading minus sign)
2449 switch (get())
2450 {
2451 case '0':
2452 case '1':
2453 case '2':
2454 case '3':
2455 case '4':
2456 case '5':
2457 case '6':
2458 case '7':
2459 case '8':
2460 case '9':
2461 {
2462 add(current);
2463 goto scan_number_any1;
2464 }
2465
2466 case '.':
2467 {
2468 add(decimal_point_char);
2469 goto scan_number_decimal1;
2470 }
2471
2472 case 'e':
2473 case 'E':
2474 {
2475 add(current);
2476 goto scan_number_exponent;
2477 }
2478
2479 default:
2480 goto scan_number_done;
2481 }
2482
2483scan_number_decimal1:
2484 // state: we just parsed a decimal point
2485 number_type = token_type::value_float;
2486 switch (get())
2487 {
2488 case '0':
2489 case '1':
2490 case '2':
2491 case '3':
2492 case '4':
2493 case '5':
2494 case '6':
2495 case '7':
2496 case '8':
2497 case '9':
2498 {
2499 add(current);
2500 goto scan_number_decimal2;
2501 }
2502
2503 default:
2504 {
2505 error_message = "invalid number; expected digit after '.'";
2506 return token_type::parse_error;
2507 }
2508 }
2509
2510scan_number_decimal2:
2511 // we just parsed at least one number after a decimal point
2512 switch (get())
2513 {
2514 case '0':
2515 case '1':
2516 case '2':
2517 case '3':
2518 case '4':
2519 case '5':
2520 case '6':
2521 case '7':
2522 case '8':
2523 case '9':
2524 {
2525 add(current);
2526 goto scan_number_decimal2;
2527 }
2528
2529 case 'e':
2530 case 'E':
2531 {
2532 add(current);
2533 goto scan_number_exponent;
2534 }
2535
2536 default:
2537 goto scan_number_done;
2538 }
2539
2540scan_number_exponent:
2541 // we just parsed an exponent
2542 number_type = token_type::value_float;
2543 switch (get())
2544 {
2545 case '+':
2546 case '-':
2547 {
2548 add(current);
2549 goto scan_number_sign;
2550 }
2551
2552 case '0':
2553 case '1':
2554 case '2':
2555 case '3':
2556 case '4':
2557 case '5':
2558 case '6':
2559 case '7':
2560 case '8':
2561 case '9':
2562 {
2563 add(current);
2564 goto scan_number_any2;
2565 }
2566
2567 default:
2568 {
2569 error_message =
2570 "invalid number; expected '+', '-', or digit after exponent";
2571 return token_type::parse_error;
2572 }
2573 }
2574
2575scan_number_sign:
2576 // we just parsed an exponent sign
2577 switch (get())
2578 {
2579 case '0':
2580 case '1':
2581 case '2':
2582 case '3':
2583 case '4':
2584 case '5':
2585 case '6':
2586 case '7':
2587 case '8':
2588 case '9':
2589 {
2590 add(current);
2591 goto scan_number_any2;
2592 }
2593
2594 default:
2595 {
2596 error_message = "invalid number; expected digit after exponent sign";
2597 return token_type::parse_error;
2598 }
2599 }
2600
2601scan_number_any2:
2602 // we just parsed a number after the exponent or exponent sign
2603 switch (get())
2604 {
2605 case '0':
2606 case '1':
2607 case '2':
2608 case '3':
2609 case '4':
2610 case '5':
2611 case '6':
2612 case '7':
2613 case '8':
2614 case '9':
2615 {
2616 add(current);
2617 goto scan_number_any2;
2618 }
2619
2620 default:
2621 goto scan_number_done;
2622 }
2623
2624scan_number_done:
2625 // unget the character after the number (we only read it to know that
2626 // we are done scanning a number)
2627 --chars_read;
2628 next_unget = true;
2629
2630 // terminate token
2631 add('\0');
2632 --yylen;
2633
2634 char* endptr = nullptr;
2635 errno = 0;
2636
2637 // try to parse integers first and fall back to floats
2638 if (number_type == token_type::value_unsigned)
2639 {
2640 const auto x = std::strtoull(yytext.data(), &endptr, 10);
2641
2642 // we checked the number format before
2643 assert(endptr == yytext.data() + yylen);
2644
2645 if (errno == 0)
2646 {
2647 value_unsigned = static_cast<number_unsigned_t>(x);
2648 if (value_unsigned == x)
2649 {
2650 return token_type::value_unsigned;
2651 }
2652 }
2653 }
2654 else if (number_type == token_type::value_integer)
2655 {
2656 const auto x = std::strtoll(yytext.data(), &endptr, 10);
2657
2658 // we checked the number format before
2659 assert(endptr == yytext.data() + yylen);
2660
2661 if (errno == 0)
2662 {
2663 value_integer = static_cast<number_integer_t>(x);
2664 if (value_integer == x)
2665 {
2666 return token_type::value_integer;
2667 }
2668 }
2669 }
2670
2671 // this code is reached if we parse a floating-point number or if an
2672 // integer conversion above failed
2673 strtof(value_float, yytext.data(), &endptr);
2674
2675 // we checked the number format before
2676 assert(endptr == yytext.data() + yylen);
2677
2678 return token_type::value_float;
2679 }
2680
2681 /*!
2682 @param[in] literal_text the literal text to expect
2683 @param[in] length the length of the passed literal text
2684 @param[in] return_type the token type to return on success
2685 */
2686 token_type scan_literal(const char* literal_text, const std::size_t length,
2687 token_type return_type)
2688 {
2689 assert(current == literal_text[0]);
2690 for (std::size_t i = 1; i < length; ++i)
2691 {
2692 if (JSON_UNLIKELY(get() != literal_text[i]))
2693 {
2694 error_message = "invalid literal";
2695 return token_type::parse_error;
2696 }
2697 }
2698 return return_type;
2699 }
2700
2701 /////////////////////
2702 // input management
2703 /////////////////////
2704
2705 /// reset yytext
2706 void reset() noexcept
2707 {
2708 yylen = 0;
2709 start_pos = chars_read - 1;
2710 }
2711
2712 /// get a character from the input
2713 int get()
2714 {
2715 ++chars_read;
2716 return next_unget ? (next_unget = false, current)
2717 : (current = ia->get_character());
2718 }
2719
2720 /// add a character to yytext
2721 void add(int c)
2722 {
2723 // resize yytext if necessary; this condition is deemed unlikely,
2724 // because we start with a 1024-byte buffer
2725 if (JSON_UNLIKELY((yylen + 1 > yytext.capacity())))
2726 {
2727 yytext.resize(2 * yytext.capacity(), '\0');
2728 }
2729 assert(yylen < yytext.size());
2730 yytext[yylen++] = static_cast<char>(c);
2731 }
2732
2733 public:
2734 /////////////////////
2735 // value getters
2736 /////////////////////
2737
2738 /// return integer value
2739 constexpr number_integer_t get_number_integer() const noexcept
2740 {
2741 return value_integer;
2742 }
2743
2744 /// return unsigned integer value
2745 constexpr number_unsigned_t get_number_unsigned() const noexcept
2746 {
2747 return value_unsigned;
2748 }
2749
2750 /// return floating-point value
2751 constexpr number_float_t get_number_float() const noexcept
2752 {
2753 return value_float;
2754 }
2755
2756 /// return string value
2757 const std::string get_string()
2758 {
2759 // yytext cannot be returned as char*, because it may contain a null
2760 // byte (parsed as "\u0000")
2761 return std::string(yytext.data(), yylen);
2762 }
2763
2764 /////////////////////
2765 // diagnostics
2766 /////////////////////
2767
2768 /// return position of last read token
2769 constexpr std::size_t get_position() const noexcept
2770 {
2771 return chars_read;
2772 }
2773
2774 /// return the last read token (for errors only)
2775 std::string get_token_string() const
2776 {
2777 // get the raw byte sequence of the last token
2778 std::string s = ia->read(start_pos, chars_read - start_pos);
2779
2780 // escape control characters
2781 std::string result;
2782 for (auto c : s)
2783 {
2784 if (c == '\0' or c == std::char_traits<char>::eof())
2785 {
2786 // ignore EOF
2787 continue;
2788 }
2789 else if ('\x00' <= c and c <= '\x1f')
2790 {
2791 // escape control characters
2792 std::stringstream ss;
2793 ss << "<U+" << std::setw(4) << std::uppercase << std::setfill('0')
2794 << std::hex << static_cast<int>(c) << ">";
2795 result += ss.str();
2796 }
2797 else
2798 {
2799 // add character as is
2800 result.push_back(c);
2801 }
2802 }
2803
2804 return result;
2805 }
2806
2807 /// return syntax error message
2808 constexpr const char* get_error_message() const noexcept
2809 {
2810 return error_message;
2811 }
2812
2813 /////////////////////
2814 // actual scanner
2815 /////////////////////
2816
2817 token_type scan()
2818 {
2819 // read next character and ignore whitespace
2820 do
2821 {
2822 get();
2823 }
2824 while (current == ' ' or current == '\t' or current == '\n' or current == '\r');
2825
2826 switch (current)
2827 {
2828 // structural characters
2829 case '[':
2830 return token_type::begin_array;
2831 case ']':
2832 return token_type::end_array;
2833 case '{':
2834 return token_type::begin_object;
2835 case '}':
2836 return token_type::end_object;
2837 case ':':
2838 return token_type::name_separator;
2839 case ',':
2840 return token_type::value_separator;
2841
2842 // literals
2843 case 't':
2844 return scan_literal("true", 4, token_type::literal_true);
2845 case 'f':
2846 return scan_literal("false", 5, token_type::literal_false);
2847 case 'n':
2848 return scan_literal("null", 4, token_type::literal_null);
2849
2850 // string
2851 case '\"':
2852 return scan_string();
2853
2854 // number
2855 case '-':
2856 case '0':
2857 case '1':
2858 case '2':
2859 case '3':
2860 case '4':
2861 case '5':
2862 case '6':
2863 case '7':
2864 case '8':
2865 case '9':
2866 return scan_number();
2867
2868 // end of input (the null byte is needed when parsing from
2869 // string literals)
2870 case '\0':
2871 case std::char_traits<char>::eof():
2872 return token_type::end_of_input;
2873
2874 // error
2875 default:
2876 error_message = "invalid literal";
2877 return token_type::parse_error;
2878 }
2879 }
2880
2881 private:
2882 /// input adapter
2883 detail::input_adapter_t ia = nullptr;
2884
2885 /// the current character
2886 int current = std::char_traits<char>::eof();
2887
2888 /// whether get() should return the last character again
2889 bool next_unget = false;
2890
2891 /// the number of characters read
2892 std::size_t chars_read = 0;
2893 /// the start position of the current token
2894 std::size_t start_pos = 0;
2895
2896 /// buffer for variable-length tokens (numbers, strings)
2897 std::vector<char> yytext = std::vector<char>(1024, '\0');
2898 /// current index in yytext
2899 std::size_t yylen = 0;
2900
2901 /// a description of occurred lexer errors
2902 const char* error_message = "";
2903
2904 // number values
2905 number_integer_t value_integer = 0;
2906 number_unsigned_t value_unsigned = 0;
2907 number_float_t value_float = 0;
2908
2909 /// the decimal point
2910 const char decimal_point_char = '.';
2911};
2912
2913/*!
2914@brief syntax analysis
2915
2916This class implements a recursive decent parser.
2917*/
2918template<typename BasicJsonType>
2919class parser
2920{
2921 using number_integer_t = typename BasicJsonType::number_integer_t;
2922 using number_unsigned_t = typename BasicJsonType::number_unsigned_t;
2923 using number_float_t = typename BasicJsonType::number_float_t;
2924 using lexer_t = lexer<BasicJsonType>;
2925 using token_type = typename lexer_t::token_type;
2926
2927 public:
2928 enum class parse_event_t : uint8_t
2929 {
2930 /// the parser read `{` and started to process a JSON object
2931 object_start,
2932 /// the parser read `}` and finished processing a JSON object
2933 object_end,
2934 /// the parser read `[` and started to process a JSON array
2935 array_start,
2936 /// the parser read `]` and finished processing a JSON array
2937 array_end,
2938 /// the parser read a key of a value in an object
2939 key,
2940 /// the parser finished reading a JSON value
2941 value
2942 };
2943
2944 using parser_callback_t =
2945 std::function<bool(int depth, parse_event_t event, BasicJsonType& parsed)>;
2946
2947 /// a parser reading from an input adapter
2948 explicit parser(detail::input_adapter_t adapter,
2949 const parser_callback_t cb = nullptr,
2950 const bool allow_exceptions_ = true)
2951 : callback(cb), m_lexer(adapter), allow_exceptions(allow_exceptions_)
2952 {}
2953
2954 /*!
2955 @brief public parser interface
2956
2957 @param[in] strict whether to expect the last token to be EOF
2958 @param[in,out] result parsed JSON value
2959
2960 @throw parse_error.101 in case of an unexpected token
2961 @throw parse_error.102 if to_unicode fails or surrogate error
2962 @throw parse_error.103 if to_unicode fails
2963 */
2964 void parse(const bool strict, BasicJsonType& result)
2965 {
2966 // read first token
2967 get_token();
2968
2969 parse_internal(true, result);
2970 result.assert_invariant();
2971
2972 // in strict mode, input must be completely read
2973 if (strict)
2974 {
2975 get_token();
2976 expect(token_type::end_of_input);
2977 }
2978
2979 // in case of an error, return discarded value
2980 if (errored)
2981 {
2982 result = value_t::discarded;
2983 return;
2984 }
2985
2986 // set top-level value to null if it was discarded by the callback
2987 // function
2988 if (result.is_discarded())
2989 {
2990 result = nullptr;
2991 }
2992 }
2993
2994 /*!
2995 @brief public accept interface
2996
2997 @param[in] strict whether to expect the last token to be EOF
2998 @return whether the input is a proper JSON text
2999 */
3000 bool accept(const bool strict = true)
3001 {
3002 // read first token
3003 get_token();
3004
3005 if (not accept_internal())
3006 {
3007 return false;
3008 }
3009
3010 // strict => last token must be EOF
3011 return not strict or (get_token() == token_type::end_of_input);
3012 }
3013
3014 private:
3015 /*!
3016 @brief the actual parser
3017 @throw parse_error.101 in case of an unexpected token
3018 @throw parse_error.102 if to_unicode fails or surrogate error
3019 @throw parse_error.103 if to_unicode fails
3020 */
3021 void parse_internal(bool keep, BasicJsonType& result)
3022 {
3023 // never parse after a parse error was detected
3024 assert(not errored);
3025
3026 // start with a discarded value
3027 if (not result.is_discarded())
3028 {
3029 result.m_value.destroy(result.m_type);
3030 result.m_type = value_t::discarded;
3031 }
3032
3033 switch (last_token)
3034 {
3035 case token_type::begin_object:
3036 {
3037 if (keep)
3038 {
3039 if (callback)
3040 {
3041 keep = callback(depth++, parse_event_t::object_start, result);
3042 }
3043
3044 if (not callback or keep)
3045 {
3046 // explicitly set result to object to cope with {}
3047 result.m_type = value_t::object;
3048 result.m_value = value_t::object;
3049 }
3050 }
3051
3052 // read next token
3053 get_token();
3054
3055 // closing } -> we are done
3056 if (last_token == token_type::end_object)
3057 {
3058 if (keep and callback and not callback(--depth, parse_event_t::object_end, result))
3059 {
3060 result.m_value.destroy(result.m_type);
3061 result.m_type = value_t::discarded;
3062 }
3063 break;
3064 }
3065
3066 // parse values
3067 std::string key;
3068 BasicJsonType value;
3069 while (true)
3070 {
3071 // store key
3072 if (not expect(token_type::value_string))
3073 {
3074 return;
3075 }
3076 key = m_lexer.get_string();
3077
3078 bool keep_tag = false;
3079 if (keep)
3080 {
3081 if (callback)
3082 {
3083 BasicJsonType k(key);
3084 keep_tag = callback(depth, parse_event_t::key, k);
3085 }
3086 else
3087 {
3088 keep_tag = true;
3089 }
3090 }
3091
3092 // parse separator (:)
3093 get_token();
3094 if (not expect(token_type::name_separator))
3095 {
3096 return;
3097 }
3098
3099 // parse and add value
3100 get_token();
3101 value.m_value.destroy(value.m_type);
3102 value.m_type = value_t::discarded;
3103 parse_internal(keep, value);
3104
3105 if (JSON_UNLIKELY(errored))
3106 {
3107 return;
3108 }
3109
3110 if (keep and keep_tag and not value.is_discarded())
3111 {
3112 result.m_value.object->emplace(std::move(key), std::move(value));
3113 }
3114
3115 // comma -> next value
3116 get_token();
3117 if (last_token == token_type::value_separator)
3118 {
3119 get_token();
3120 continue;
3121 }
3122
3123 // closing }
3124 if (not expect(token_type::end_object))
3125 {
3126 return;
3127 }
3128 break;
3129 }
3130
3131 if (keep and callback and not callback(--depth, parse_event_t::object_end, result))
3132 {
3133 result.m_value.destroy(result.m_type);
3134 result.m_type = value_t::discarded;
3135 }
3136 break;
3137 }
3138
3139 case token_type::begin_array:
3140 {
3141 if (keep)
3142 {
3143 if (callback)
3144 {
3145 keep = callback(depth++, parse_event_t::array_start, result);
3146 }
3147
3148 if (not callback or keep)
3149 {
3150 // explicitly set result to array to cope with []
3151 result.m_type = value_t::array;
3152 result.m_value = value_t::array;
3153 }
3154 }
3155
3156 // read next token
3157 get_token();
3158
3159 // closing ] -> we are done
3160 if (last_token == token_type::end_array)
3161 {
3162 if (callback and not callback(--depth, parse_event_t::array_end, result))
3163 {
3164 result.m_value.destroy(result.m_type);
3165 result.m_type = value_t::discarded;
3166 }
3167 break;
3168 }
3169
3170 // parse values
3171 BasicJsonType value;
3172 while (true)
3173 {
3174 // parse value
3175 value.m_value.destroy(value.m_type);
3176 value.m_type = value_t::discarded;
3177 parse_internal(keep, value);
3178
3179 if (JSON_UNLIKELY(errored))
3180 {
3181 return;
3182 }
3183
3184 if (keep and not value.is_discarded())
3185 {
3186 result.m_value.array->push_back(std::move(value));
3187 }
3188
3189 // comma -> next value
3190 get_token();
3191 if (last_token == token_type::value_separator)
3192 {
3193 get_token();
3194 continue;
3195 }
3196
3197 // closing ]
3198 if (not expect(token_type::end_array))
3199 {
3200 return;
3201 }
3202 break;
3203 }
3204
3205 if (keep and callback and not callback(--depth, parse_event_t::array_end, result))
3206 {
3207 result.m_value.destroy(result.m_type);
3208 result.m_type = value_t::discarded;
3209 }
3210 break;
3211 }
3212
3213 case token_type::literal_null:
3214 {
3215 result.m_type = value_t::null;
3216 break;
3217 }
3218
3219 case token_type::value_string:
3220 {
3221 result.m_type = value_t::string;
3222 result.m_value = m_lexer.get_string();
3223 break;
3224 }
3225
3226 case token_type::literal_true:
3227 {
3228 result.m_type = value_t::boolean;
3229 result.m_value = true;
3230 break;
3231 }
3232
3233 case token_type::literal_false:
3234 {
3235 result.m_type = value_t::boolean;
3236 result.m_value = false;
3237 break;
3238 }
3239
3240 case token_type::value_unsigned:
3241 {
3242 result.m_type = value_t::number_unsigned;
3243 result.m_value = m_lexer.get_number_unsigned();
3244 break;
3245 }
3246
3247 case token_type::value_integer:
3248 {
3249 result.m_type = value_t::number_integer;
3250 result.m_value = m_lexer.get_number_integer();
3251 break;
3252 }
3253
3254 case token_type::value_float:
3255 {
3256 result.m_type = value_t::number_float;
3257 result.m_value = m_lexer.get_number_float();
3258
3259 // throw in case of infinity or NAN
3260 if (JSON_UNLIKELY(not std::isfinite(result.m_value.number_float)))
3261 {
3262 if (allow_exceptions)
3263 {
3264 JSON_THROW(out_of_range::create(406, "number overflow parsing '" +
3265 m_lexer.get_token_string() + "'"));
3266 }
3267 expect(token_type::uninitialized);
3268 }
3269 break;
3270 }
3271
3272 case token_type::parse_error:
3273 {
3274 // using "uninitialized" to avoid "expected" message
3275 if (not expect(token_type::uninitialized))
3276 {
3277 return;
3278 }
3279 break; // LCOV_EXCL_LINE
3280 }
3281
3282 default:
3283 {
3284 // the last token was unexpected; we expected a value
3285 if (not expect(token_type::literal_or_value))
3286 {
3287 return;
3288 }
3289 break; // LCOV_EXCL_LINE
3290 }
3291 }
3292
3293 if (keep and callback and not callback(depth, parse_event_t::value, result))
3294 {
3295 result.m_type = value_t::discarded;
3296 }
3297 }
3298
3299 /*!
3300 @brief the acutal acceptor
3301
3302 @invariant 1. The last token is not yet processed. Therefore, the caller
3303 of this function must make sure a token has been read.
3304 2. When this function returns, the last token is processed.
3305 That is, the last read character was already considered.
3306
3307 This invariant makes sure that no token needs to be "unput".
3308 */
3309 bool accept_internal()
3310 {
3311 switch (last_token)
3312 {
3313 case token_type::begin_object:
3314 {
3315 // read next token
3316 get_token();
3317
3318 // closing } -> we are done
3319 if (last_token == token_type::end_object)
3320 {
3321 return true;
3322 }
3323
3324 // parse values
3325 while (true)
3326 {
3327 // parse key
3328 if (last_token != token_type::value_string)
3329 {
3330 return false;
3331 }
3332
3333 // parse separator (:)
3334 get_token();
3335 if (last_token != token_type::name_separator)
3336 {
3337 return false;
3338 }
3339
3340 // parse value
3341 get_token();
3342 if (not accept_internal())
3343 {
3344 return false;
3345 }
3346
3347 // comma -> next value
3348 get_token();
3349 if (last_token == token_type::value_separator)
3350 {
3351 get_token();
3352 continue;
3353 }
3354
3355 // closing }
3356 return (last_token == token_type::end_object);
3357 }
3358 }
3359
3360 case token_type::begin_array:
3361 {
3362 // read next token
3363 get_token();
3364
3365 // closing ] -> we are done
3366 if (last_token == token_type::end_array)
3367 {
3368 return true;
3369 }
3370
3371 // parse values
3372 while (true)
3373 {
3374 // parse value
3375 if (not accept_internal())
3376 {
3377 return false;
3378 }
3379
3380 // comma -> next value
3381 get_token();
3382 if (last_token == token_type::value_separator)
3383 {
3384 get_token();
3385 continue;
3386 }
3387
3388 // closing ]
3389 return (last_token == token_type::end_array);
3390 }
3391 }
3392
3393 case token_type::value_float:
3394 {
3395 // reject infinity or NAN
3396 return std::isfinite(m_lexer.get_number_float());
3397 }
3398
3399 case token_type::literal_false:
3400 case token_type::literal_null:
3401 case token_type::literal_true:
3402 case token_type::value_integer:
3403 case token_type::value_string:
3404 case token_type::value_unsigned:
3405 return true;
3406
3407 default: // the last token was unexpected
3408 return false;
3409 }
3410 }
3411
3412 /// get next token from lexer
3413 token_type get_token()
3414 {
3415 return (last_token = m_lexer.scan());
3416 }
3417
3418 /*!
3419 @throw parse_error.101 if expected token did not occur
3420 */
3421 bool expect(token_type t)
3422 {
3423 if (JSON_UNLIKELY(t != last_token))
3424 {
3425 errored = true;
3426 expected = t;
3427 if (allow_exceptions)
3428 {
3429 throw_exception();
3430 }
3431 else
3432 {
3433 return false;
3434 }
3435 }
3436
3437 return true;
3438 }
3439
3440 [[noreturn]] void throw_exception() const
3441 {
3442 std::string error_msg = "syntax error - ";
3443 if (last_token == token_type::parse_error)
3444 {
3445 error_msg += std::string(m_lexer.get_error_message()) + "; last read: '" +
3446 m_lexer.get_token_string() + "'";
3447 }
3448 else
3449 {
3450 error_msg += "unexpected " + std::string(lexer_t::token_type_name(last_token));
3451 }
3452
3453 if (expected != token_type::uninitialized)
3454 {
3455 error_msg += "; expected " + std::string(lexer_t::token_type_name(expected));
3456 }
3457
3458 JSON_THROW(parse_error::create(101, m_lexer.get_position(), error_msg));
3459 }
3460
3461 private:
3462 /// current level of recursion
3463 int depth = 0;
3464 /// callback function
3465 const parser_callback_t callback = nullptr;
3466 /// the type of the last read token
3467 token_type last_token = token_type::uninitialized;
3468 /// the lexer
3469 lexer_t m_lexer;
3470 /// whether a syntax error occurred
3471 bool errored = false;
3472 /// possible reason for the syntax error
3473 token_type expected = token_type::uninitialized;
3474 /// whether to throw exceptions in case of errors
3475 const bool allow_exceptions = true;
3476};
3477
3478///////////////
3479// iterators //
3480///////////////
3481
3482/*!
3483@brief an iterator for primitive JSON types
3484
3485This class models an iterator for primitive JSON types (boolean, number,
3486string). It's only purpose is to allow the iterator/const_iterator classes
3487to "iterate" over primitive values. Internally, the iterator is modeled by
3488a `difference_type` variable. Value begin_value (`0`) models the begin,
3489end_value (`1`) models past the end.
3490*/
3491class primitive_iterator_t
3492{
3493 public:
3494 using difference_type = std::ptrdiff_t;
3495
3496 constexpr difference_type get_value() const noexcept
3497 {
3498 return m_it;
3499 }
3500
3501 /// set iterator to a defined beginning
3502 void set_begin() noexcept
3503 {
3504 m_it = begin_value;
3505 }
3506
3507 /// set iterator to a defined past the end
3508 void set_end() noexcept
3509 {
3510 m_it = end_value;
3511 }
3512
3513 /// return whether the iterator can be dereferenced
3514 constexpr bool is_begin() const noexcept
3515 {
3516 return m_it == begin_value;
3517 }
3518
3519 /// return whether the iterator is at end
3520 constexpr bool is_end() const noexcept
3521 {
3522 return m_it == end_value;
3523 }
3524
3525 friend constexpr bool operator==(primitive_iterator_t lhs, primitive_iterator_t rhs) noexcept
3526 {
3527 return lhs.m_it == rhs.m_it;
3528 }
3529
3530 friend constexpr bool operator<(primitive_iterator_t lhs, primitive_iterator_t rhs) noexcept
3531 {
3532 return lhs.m_it < rhs.m_it;
3533 }
3534
3535 primitive_iterator_t operator+(difference_type i)
3536 {
3537 auto result = *this;
3538 result += i;
3539 return result;
3540 }
3541
3542 friend constexpr difference_type operator-(primitive_iterator_t lhs, primitive_iterator_t rhs) noexcept
3543 {
3544 return lhs.m_it - rhs.m_it;
3545 }
3546
3547 friend std::ostream& operator<<(std::ostream& os, primitive_iterator_t it)
3548 {
3549 return os << it.m_it;
3550 }
3551
3552 primitive_iterator_t& operator++()
3553 {
3554 ++m_it;
3555 return *this;
3556 }
3557
3558 primitive_iterator_t operator++(int)
3559 {
3560 auto result = *this;
3561 m_it++;
3562 return result;
3563 }
3564
3565 primitive_iterator_t& operator--()
3566 {
3567 --m_it;
3568 return *this;
3569 }
3570
3571 primitive_iterator_t operator--(int)
3572 {
3573 auto result = *this;
3574 m_it--;
3575 return result;
3576 }
3577
3578 primitive_iterator_t& operator+=(difference_type n)
3579 {
3580 m_it += n;
3581 return *this;
3582 }
3583
3584 primitive_iterator_t& operator-=(difference_type n)
3585 {
3586 m_it -= n;
3587 return *this;
3588 }
3589
3590 private:
3591 static constexpr difference_type begin_value = 0;
3592 static constexpr difference_type end_value = begin_value + 1;
3593
3594 /// iterator as signed integer type
3595 difference_type m_it = (std::numeric_limits<std::ptrdiff_t>::min)();
3596};
3597
3598/*!
3599@brief an iterator value
3600
3601@note This structure could easily be a union, but MSVC currently does not allow
3602unions members with complex constructors, see https://github.com/nlohmann/json/pull/105.
3603*/
3604template<typename BasicJsonType> struct internal_iterator
3605{
3606 /// iterator for JSON objects
3607 typename BasicJsonType::object_t::iterator object_iterator {};
3608 /// iterator for JSON arrays
3609 typename BasicJsonType::array_t::iterator array_iterator {};
3610 /// generic iterator for all other types
3611 primitive_iterator_t primitive_iterator {};
3612};
3613
3614template<typename IteratorType> class iteration_proxy;
3615
3616/*!
3617@brief a template for a random access iterator for the @ref basic_json class
3618
3619This class implements a both iterators (iterator and const_iterator) for the
3620@ref basic_json class.
3621
3622@note An iterator is called *initialized* when a pointer to a JSON value has
3623 been set (e.g., by a constructor or a copy assignment). If the iterator is
3624 default-constructed, it is *uninitialized* and most methods are undefined.
3625 **The library uses assertions to detect calls on uninitialized iterators.**
3626
3627@requirement The class satisfies the following concept requirements:
3628-
3629[RandomAccessIterator](http://en.cppreference.com/w/cpp/concept/RandomAccessIterator):
3630 The iterator that can be moved to point (forward and backward) to any
3631 element in constant time.
3632
3633@since version 1.0.0, simplified in version 2.0.9
3634*/
3635template<typename BasicJsonType>
3636class iter_impl : public std::iterator<std::random_access_iterator_tag, BasicJsonType>
3637{
3638 /// allow basic_json to access private members
3639 friend iter_impl<typename std::conditional<std::is_const<BasicJsonType>::value, typename std::remove_const<BasicJsonType>::type, const BasicJsonType>::type>;
3640 friend BasicJsonType;
3641 friend iteration_proxy<iter_impl>;
3642
3643 using object_t = typename BasicJsonType::object_t;
3644 using array_t = typename BasicJsonType::array_t;
3645 // make sure BasicJsonType is basic_json or const basic_json
3646 static_assert(is_basic_json<typename std::remove_const<BasicJsonType>::type>::value,
3647 "iter_impl only accepts (const) basic_json");
3648
3649 public:
3650 /// the type of the values when the iterator is dereferenced
3651 using value_type = typename BasicJsonType::value_type;
3652 /// a type to represent differences between iterators
3653 using difference_type = typename BasicJsonType::difference_type;
3654 /// defines a pointer to the type iterated over (value_type)
3655 using pointer = typename std::conditional<std::is_const<BasicJsonType>::value,
3656 typename BasicJsonType::const_pointer,
3657 typename BasicJsonType::pointer>::type;
3658 /// defines a reference to the type iterated over (value_type)
3659 using reference =
3660 typename std::conditional<std::is_const<BasicJsonType>::value,
3661 typename BasicJsonType::const_reference,
3662 typename BasicJsonType::reference>::type;
3663 /// the category of the iterator
3664 using iterator_category = std::bidirectional_iterator_tag;
3665
3666 /// default constructor
3667 iter_impl() = default;
3668
3669 /*!
3670 @brief constructor for a given JSON instance
3671 @param[in] object pointer to a JSON object for this iterator
3672 @pre object != nullptr
3673 @post The iterator is initialized; i.e. `m_object != nullptr`.
3674 */
3675 explicit iter_impl(pointer object) noexcept : m_object(object)
3676 {
3677 assert(m_object != nullptr);
3678
3679 switch (m_object->m_type)
3680 {
3681 case value_t::object:
3682 {
3683 m_it.object_iterator = typename object_t::iterator();
3684 break;
3685 }
3686
3687 case value_t::array:
3688 {
3689 m_it.array_iterator = typename array_t::iterator();
3690 break;
3691 }
3692
3693 default:
3694 {
3695 m_it.primitive_iterator = primitive_iterator_t();
3696 break;
3697 }
3698 }
3699 }
3700
3701 /*!
3702 @note The conventional copy constructor and copy assignment are implicitly
3703 defined. Combined with the following converting constructor and
3704 assignment, they support: (1) copy from iterator to iterator, (2)
3705 copy from const iterator to const iterator, and (3) conversion from
3706 iterator to const iterator. However conversion from const iterator
3707 to iterator is not defined.
3708 */
3709
3710 /*!
3711 @brief converting constructor
3712 @param[in] other non-const iterator to copy from
3713 @note It is not checked whether @a other is initialized.
3714 */
3715 iter_impl(const iter_impl<typename std::remove_const<BasicJsonType>::type>& other) noexcept
3716 : m_object(other.m_object), m_it(other.m_it) {}
3717
3718 /*!
3719 @brief converting assignment
3720 @param[in,out] other non-const iterator to copy from
3721 @return const/non-const iterator
3722 @note It is not checked whether @a other is initialized.
3723 */
3724 iter_impl& operator=(const iter_impl<typename std::remove_const<BasicJsonType>::type>& other) noexcept
3725 {
3726 m_object = other.m_object;
3727 m_it = other.m_it;
3728 return *this;
3729 }
3730
3731 private:
3732 /*!
3733 @brief set the iterator to the first value
3734 @pre The iterator is initialized; i.e. `m_object != nullptr`.
3735 */
3736 void set_begin() noexcept
3737 {
3738 assert(m_object != nullptr);
3739
3740 switch (m_object->m_type)
3741 {
3742 case value_t::object:
3743 {
3744 m_it.object_iterator = m_object->m_value.object->begin();
3745 break;
3746 }
3747
3748 case value_t::array:
3749 {
3750 m_it.array_iterator = m_object->m_value.array->begin();
3751 break;
3752 }
3753
3754 case value_t::null:
3755 {
3756 // set to end so begin()==end() is true: null is empty
3757 m_it.primitive_iterator.set_end();
3758 break;
3759 }
3760
3761 default:
3762 {
3763 m_it.primitive_iterator.set_begin();
3764 break;
3765 }
3766 }
3767 }
3768
3769 /*!
3770 @brief set the iterator past the last value
3771 @pre The iterator is initialized; i.e. `m_object != nullptr`.
3772 */
3773 void set_end() noexcept
3774 {
3775 assert(m_object != nullptr);
3776
3777 switch (m_object->m_type)
3778 {
3779 case value_t::object:
3780 {
3781 m_it.object_iterator = m_object->m_value.object->end();
3782 break;
3783 }
3784
3785 case value_t::array:
3786 {
3787 m_it.array_iterator = m_object->m_value.array->end();
3788 break;
3789 }
3790
3791 default:
3792 {
3793 m_it.primitive_iterator.set_end();
3794 break;
3795 }
3796 }
3797 }
3798
3799 public:
3800 /*!
3801 @brief return a reference to the value pointed to by the iterator
3802 @pre The iterator is initialized; i.e. `m_object != nullptr`.
3803 */
3804 reference operator*() const
3805 {
3806 assert(m_object != nullptr);
3807
3808 switch (m_object->m_type)
3809 {
3810 case value_t::object:
3811 {
3812 assert(m_it.object_iterator != m_object->m_value.object->end());
3813 return m_it.object_iterator->second;
3814 }
3815
3816 case value_t::array:
3817 {
3818 assert(m_it.array_iterator != m_object->m_value.array->end());
3819 return *m_it.array_iterator;
3820 }
3821
3822 case value_t::null:
3823 JSON_THROW(invalid_iterator::create(214, "cannot get value"));
3824
3825 default:
3826 {
3827 if (JSON_LIKELY(m_it.primitive_iterator.is_begin()))
3828 {
3829 return *m_object;
3830 }
3831
3832 JSON_THROW(invalid_iterator::create(214, "cannot get value"));
3833 }
3834 }
3835 }
3836
3837 /*!
3838 @brief dereference the iterator
3839 @pre The iterator is initialized; i.e. `m_object != nullptr`.
3840 */
3841 pointer operator->() const
3842 {
3843 assert(m_object != nullptr);
3844
3845 switch (m_object->m_type)
3846 {
3847 case value_t::object:
3848 {
3849 assert(m_it.object_iterator != m_object->m_value.object->end());
3850 return &(m_it.object_iterator->second);
3851 }
3852
3853 case value_t::array:
3854 {
3855 assert(m_it.array_iterator != m_object->m_value.array->end());
3856 return &*m_it.array_iterator;
3857 }
3858
3859 default:
3860 {
3861 if (JSON_LIKELY(m_it.primitive_iterator.is_begin()))
3862 {
3863 return m_object;
3864 }
3865
3866 JSON_THROW(invalid_iterator::create(214, "cannot get value"));
3867 }
3868 }
3869 }
3870
3871 /*!
3872 @brief post-increment (it++)
3873 @pre The iterator is initialized; i.e. `m_object != nullptr`.
3874 */
3875 iter_impl operator++(int)
3876 {
3877 auto result = *this;
3878 ++(*this);
3879 return result;
3880 }
3881
3882 /*!
3883 @brief pre-increment (++it)
3884 @pre The iterator is initialized; i.e. `m_object != nullptr`.
3885 */
3886 iter_impl& operator++()
3887 {
3888 assert(m_object != nullptr);
3889
3890 switch (m_object->m_type)
3891 {
3892 case value_t::object:
3893 {
3894 std::advance(m_it.object_iterator, 1);
3895 break;
3896 }
3897
3898 case value_t::array:
3899 {
3900 std::advance(m_it.array_iterator, 1);
3901 break;
3902 }
3903
3904 default:
3905 {
3906 ++m_it.primitive_iterator;
3907 break;
3908 }
3909 }
3910
3911 return *this;
3912 }
3913
3914 /*!
3915 @brief post-decrement (it--)
3916 @pre The iterator is initialized; i.e. `m_object != nullptr`.
3917 */
3918 iter_impl operator--(int)
3919 {
3920 auto result = *this;
3921 --(*this);
3922 return result;
3923 }
3924
3925 /*!
3926 @brief pre-decrement (--it)
3927 @pre The iterator is initialized; i.e. `m_object != nullptr`.
3928 */
3929 iter_impl& operator--()
3930 {
3931 assert(m_object != nullptr);
3932
3933 switch (m_object->m_type)
3934 {
3935 case value_t::object:
3936 {
3937 std::advance(m_it.object_iterator, -1);
3938 break;
3939 }
3940
3941 case value_t::array:
3942 {
3943 std::advance(m_it.array_iterator, -1);
3944 break;
3945 }
3946
3947 default:
3948 {
3949 --m_it.primitive_iterator;
3950 break;
3951 }
3952 }
3953
3954 return *this;
3955 }
3956
3957 /*!
3958 @brief comparison: equal
3959 @pre The iterator is initialized; i.e. `m_object != nullptr`.
3960 */
3961 bool operator==(const iter_impl& other) const
3962 {
3963 // if objects are not the same, the comparison is undefined
3964 if (JSON_UNLIKELY(m_object != other.m_object))
3965 {
3966 JSON_THROW(invalid_iterator::create(212, "cannot compare iterators of different containers"));
3967 }
3968
3969 assert(m_object != nullptr);
3970
3971 switch (m_object->m_type)
3972 {
3973 case value_t::object:
3974 return (m_it.object_iterator == other.m_it.object_iterator);
3975
3976 case value_t::array:
3977 return (m_it.array_iterator == other.m_it.array_iterator);
3978
3979 default:
3980 return (m_it.primitive_iterator == other.m_it.primitive_iterator);
3981 }
3982 }
3983
3984 /*!
3985 @brief comparison: not equal
3986 @pre The iterator is initialized; i.e. `m_object != nullptr`.
3987 */
3988 bool operator!=(const iter_impl& other) const
3989 {
3990 return not operator==(other);
3991 }
3992
3993 /*!
3994 @brief comparison: smaller
3995 @pre The iterator is initialized; i.e. `m_object != nullptr`.
3996 */
3997 bool operator<(const iter_impl& other) const
3998 {
3999 // if objects are not the same, the comparison is undefined
4000 if (JSON_UNLIKELY(m_object != other.m_object))
4001 {
4002 JSON_THROW(invalid_iterator::create(212, "cannot compare iterators of different containers"));
4003 }
4004
4005 assert(m_object != nullptr);
4006
4007 switch (m_object->m_type)
4008 {
4009 case value_t::object:
4010 JSON_THROW(invalid_iterator::create(213, "cannot compare order of object iterators"));
4011
4012 case value_t::array:
4013 return (m_it.array_iterator < other.m_it.array_iterator);
4014
4015 default:
4016 return (m_it.primitive_iterator < other.m_it.primitive_iterator);
4017 }
4018 }
4019
4020 /*!
4021 @brief comparison: less than or equal
4022 @pre The iterator is initialized; i.e. `m_object != nullptr`.
4023 */
4024 bool operator<=(const iter_impl& other) const
4025 {
4026 return not other.operator < (*this);
4027 }
4028
4029 /*!
4030 @brief comparison: greater than
4031 @pre The iterator is initialized; i.e. `m_object != nullptr`.
4032 */
4033 bool operator>(const iter_impl& other) const
4034 {
4035 return not operator<=(other);
4036 }
4037
4038 /*!
4039 @brief comparison: greater than or equal
4040 @pre The iterator is initialized; i.e. `m_object != nullptr`.
4041 */
4042 bool operator>=(const iter_impl& other) const
4043 {
4044 return not operator<(other);
4045 }
4046
4047 /*!
4048 @brief add to iterator
4049 @pre The iterator is initialized; i.e. `m_object != nullptr`.
4050 */
4051 iter_impl& operator+=(difference_type i)
4052 {
4053 assert(m_object != nullptr);
4054
4055 switch (m_object->m_type)
4056 {
4057 case value_t::object:
4058 JSON_THROW(invalid_iterator::create(209, "cannot use offsets with object iterators"));
4059
4060 case value_t::array:
4061 {
4062 std::advance(m_it.array_iterator, i);
4063 break;
4064 }
4065
4066 default:
4067 {
4068 m_it.primitive_iterator += i;
4069 break;
4070 }
4071 }
4072
4073 return *this;
4074 }
4075
4076 /*!
4077 @brief subtract from iterator
4078 @pre The iterator is initialized; i.e. `m_object != nullptr`.
4079 */
4080 iter_impl& operator-=(difference_type i)
4081 {
4082 return operator+=(-i);
4083 }
4084
4085 /*!
4086 @brief add to iterator
4087 @pre The iterator is initialized; i.e. `m_object != nullptr`.
4088 */
4089 iter_impl operator+(difference_type i) const
4090 {
4091 auto result = *this;
4092 result += i;
4093 return result;
4094 }
4095
4096 /*!
4097 @brief addition of distance and iterator
4098 @pre The iterator is initialized; i.e. `m_object != nullptr`.
4099 */
4100 friend iter_impl operator+(difference_type i, const iter_impl& it)
4101 {
4102 auto result = it;
4103 result += i;
4104 return result;
4105 }
4106
4107 /*!
4108 @brief subtract from iterator
4109 @pre The iterator is initialized; i.e. `m_object != nullptr`.
4110 */
4111 iter_impl operator-(difference_type i) const
4112 {
4113 auto result = *this;
4114 result -= i;
4115 return result;
4116 }
4117
4118 /*!
4119 @brief return difference
4120 @pre The iterator is initialized; i.e. `m_object != nullptr`.
4121 */
4122 difference_type operator-(const iter_impl& other) const
4123 {
4124 assert(m_object != nullptr);
4125
4126 switch (m_object->m_type)
4127 {
4128 case value_t::object:
4129 JSON_THROW(invalid_iterator::create(209, "cannot use offsets with object iterators"));
4130
4131 case value_t::array:
4132 return m_it.array_iterator - other.m_it.array_iterator;
4133
4134 default:
4135 return m_it.primitive_iterator - other.m_it.primitive_iterator;
4136 }
4137 }
4138
4139 /*!
4140 @brief access to successor
4141 @pre The iterator is initialized; i.e. `m_object != nullptr`.
4142 */
4143 reference operator[](difference_type n) const
4144 {
4145 assert(m_object != nullptr);
4146
4147 switch (m_object->m_type)
4148 {
4149 case value_t::object:
4150 JSON_THROW(invalid_iterator::create(208, "cannot use operator[] for object iterators"));
4151
4152 case value_t::array:
4153 return *std::next(m_it.array_iterator, n);
4154
4155 case value_t::null:
4156 JSON_THROW(invalid_iterator::create(214, "cannot get value"));
4157
4158 default:
4159 {
4160 if (JSON_LIKELY(m_it.primitive_iterator.get_value() == -n))
4161 {
4162 return *m_object;
4163 }
4164
4165 JSON_THROW(invalid_iterator::create(214, "cannot get value"));
4166 }
4167 }
4168 }
4169
4170 /*!
4171 @brief return the key of an object iterator
4172 @pre The iterator is initialized; i.e. `m_object != nullptr`.
4173 */
4174 typename object_t::key_type key() const
4175 {
4176 assert(m_object != nullptr);
4177
4178 if (JSON_LIKELY(m_object->is_object()))
4179 {
4180 return m_it.object_iterator->first;
4181 }
4182
4183 JSON_THROW(invalid_iterator::create(207, "cannot use key() for non-object iterators"));
4184 }
4185
4186 /*!
4187 @brief return the value of an iterator
4188 @pre The iterator is initialized; i.e. `m_object != nullptr`.
4189 */
4190 reference value() const
4191 {
4192 return operator*();
4193 }
4194
4195 private:
4196 /// associated JSON instance
4197 pointer m_object = nullptr;
4198 /// the actual iterator of the associated instance
4199 internal_iterator<typename std::remove_const<BasicJsonType>::type> m_it = {};
4200};
4201
4202/// proxy class for the iterator_wrapper functions
4203template<typename IteratorType> class iteration_proxy
4204{
4205 private:
4206 /// helper class for iteration
4207 class iteration_proxy_internal
4208 {
4209 private:
4210 /// the iterator
4211 IteratorType anchor;
4212 /// an index for arrays (used to create key names)
4213 std::size_t array_index = 0;
4214
4215 public:
4216 explicit iteration_proxy_internal(IteratorType it) noexcept : anchor(it) {}
4217
4218 /// dereference operator (needed for range-based for)
4219 iteration_proxy_internal& operator*()
4220 {
4221 return *this;
4222 }
4223
4224 /// increment operator (needed for range-based for)
4225 iteration_proxy_internal& operator++()
4226 {
4227 ++anchor;
4228 ++array_index;
4229
4230 return *this;
4231 }
4232
4233 /// inequality operator (needed for range-based for)
4234 bool operator!=(const iteration_proxy_internal& o) const noexcept
4235 {
4236 return anchor != o.anchor;
4237 }
4238
4239 /// return key of the iterator
4240 std::string key() const
4241 {
4242 assert(anchor.m_object != nullptr);
4243
4244 switch (anchor.m_object->type())
4245 {
4246 // use integer array index as key
4247 case value_t::array:
4248 return std::to_string(array_index);
4249
4250 // use key from the object
4251 case value_t::object:
4252 return anchor.key();
4253
4254 // use an empty key for all primitive types
4255 default:
4256 return "";
4257 }
4258 }
4259
4260 /// return value of the iterator
4261 typename IteratorType::reference value() const
4262 {
4263 return anchor.value();
4264 }
4265 };
4266
4267 /// the container to iterate
4268 typename IteratorType::reference container;
4269
4270 public:
4271 /// construct iteration proxy from a container
4272 explicit iteration_proxy(typename IteratorType::reference cont)
4273 : container(cont) {}
4274
4275 /// return iterator begin (needed for range-based for)
4276 iteration_proxy_internal begin() noexcept
4277 {
4278 return iteration_proxy_internal(container.begin());
4279 }
4280
4281 /// return iterator end (needed for range-based for)
4282 iteration_proxy_internal end() noexcept
4283 {
4284 return iteration_proxy_internal(container.end());
4285 }
4286};
4287
4288/*!
4289@brief a template for a reverse iterator class
4290
4291@tparam Base the base iterator type to reverse. Valid types are @ref
4292iterator (to create @ref reverse_iterator) and @ref const_iterator (to
4293create @ref const_reverse_iterator).
4294
4295@requirement The class satisfies the following concept requirements:
4296-
4297[RandomAccessIterator](http://en.cppreference.com/w/cpp/concept/RandomAccessIterator):
4298 The iterator that can be moved to point (forward and backward) to any
4299 element in constant time.
4300- [OutputIterator](http://en.cppreference.com/w/cpp/concept/OutputIterator):
4301 It is possible to write to the pointed-to element (only if @a Base is
4302 @ref iterator).
4303
4304@since version 1.0.0
4305*/
4306template<typename Base>
4307class json_reverse_iterator : public std::reverse_iterator<Base>
4308{
4309 public:
4310 using difference_type = std::ptrdiff_t;
4311 /// shortcut to the reverse iterator adaptor
4312 using base_iterator = std::reverse_iterator<Base>;
4313 /// the reference type for the pointed-to element
4314 using reference = typename Base::reference;
4315
4316 /// create reverse iterator from iterator
4317 json_reverse_iterator(const typename base_iterator::iterator_type& it) noexcept
4318 : base_iterator(it) {}
4319
4320 /// create reverse iterator from base class
4321 json_reverse_iterator(const base_iterator& it) noexcept : base_iterator(it) {}
4322
4323 /// post-increment (it++)
4324 json_reverse_iterator operator++(int)
4325 {
4326 return static_cast<json_reverse_iterator>(base_iterator::operator++(1));
4327 }
4328
4329 /// pre-increment (++it)
4330 json_reverse_iterator& operator++()
4331 {
4332 return static_cast<json_reverse_iterator&>(base_iterator::operator++());
4333 }
4334
4335 /// post-decrement (it--)
4336 json_reverse_iterator operator--(int)
4337 {
4338 return static_cast<json_reverse_iterator>(base_iterator::operator--(1));
4339 }
4340
4341 /// pre-decrement (--it)
4342 json_reverse_iterator& operator--()
4343 {
4344 return static_cast<json_reverse_iterator&>(base_iterator::operator--());
4345 }
4346
4347 /// add to iterator
4348 json_reverse_iterator& operator+=(difference_type i)
4349 {
4350 return static_cast<json_reverse_iterator&>(base_iterator::operator+=(i));
4351 }
4352
4353 /// add to iterator
4354 json_reverse_iterator operator+(difference_type i) const
4355 {
4356 return static_cast<json_reverse_iterator>(base_iterator::operator+(i));
4357 }
4358
4359 /// subtract from iterator
4360 json_reverse_iterator operator-(difference_type i) const
4361 {
4362 return static_cast<json_reverse_iterator>(base_iterator::operator-(i));
4363 }
4364
4365 /// return difference
4366 difference_type operator-(const json_reverse_iterator& other) const
4367 {
4368 return base_iterator(*this) - base_iterator(other);
4369 }
4370
4371 /// access to successor
4372 reference operator[](difference_type n) const
4373 {
4374 return *(this->operator+(n));
4375 }
4376
4377 /// return the key of an object iterator
4378 auto key() const -> decltype(std::declval<Base>().key())
4379 {
4380 auto it = --this->base();
4381 return it.key();
4382 }
4383
4384 /// return the value of an iterator
4385 reference value() const
4386 {
4387 auto it = --this->base();
4388 return it.operator * ();
4389 }
4390};
4391
4392/////////////////////
4393// output adapters //
4394/////////////////////
4395
4396/// abstract output adapter interface
4397template<typename CharType> struct output_adapter_protocol
4398{
4399 virtual void write_character(CharType c) = 0;
4400 virtual void write_characters(const CharType* s, std::size_t length) = 0;
4401 virtual ~output_adapter_protocol() = default;
4402};
4403
4404/// a type to simplify interfaces
4405template<typename CharType>
4406using output_adapter_t = std::shared_ptr<output_adapter_protocol<CharType>>;
4407
4408/// output adapter for byte vectors
4409template<typename CharType>
4410class output_vector_adapter : public output_adapter_protocol<CharType>
4411{
4412 public:
4413 explicit output_vector_adapter(std::vector<CharType>& vec) : v(vec) {}
4414
4415 void write_character(CharType c) override
4416 {
4417 v.push_back(c);
4418 }
4419
4420 void write_characters(const CharType* s, std::size_t length) override
4421 {
4422 std::copy(s, s + length, std::back_inserter(v));
4423 }
4424
4425 private:
4426 std::vector<CharType>& v;
4427};
4428
4429/// output adapter for output streams
4430template<typename CharType>
4431class output_stream_adapter : public output_adapter_protocol<CharType>
4432{
4433 public:
4434 explicit output_stream_adapter(std::basic_ostream<CharType>& s) : stream(s) {}
4435
4436 void write_character(CharType c) override
4437 {
4438 stream.put(c);
4439 }
4440
4441 void write_characters(const CharType* s, std::size_t length) override
4442 {
4443 stream.write(s, static_cast<std::streamsize>(length));
4444 }
4445
4446 private:
4447 std::basic_ostream<CharType>& stream;
4448};
4449
4450/// output adapter for basic_string
4451template<typename CharType>
4452class output_string_adapter : public output_adapter_protocol<CharType>
4453{
4454 public:
4455 explicit output_string_adapter(std::basic_string<CharType>& s) : str(s) {}
4456
4457 void write_character(CharType c) override
4458 {
4459 str.push_back(c);
4460 }
4461
4462 void write_characters(const CharType* s, std::size_t length) override
4463 {
4464 str.append(s, length);
4465 }
4466
4467 private:
4468 std::basic_string<CharType>& str;
4469};
4470
4471template<typename CharType>
4472class output_adapter
4473{
4474 public:
4475 output_adapter(std::vector<CharType>& vec)
4476 : oa(std::make_shared<output_vector_adapter<CharType>>(vec)) {}
4477
4478 output_adapter(std::basic_ostream<CharType>& s)
4479 : oa(std::make_shared<output_stream_adapter<CharType>>(s)) {}
4480
4481 output_adapter(std::basic_string<CharType>& s)
4482 : oa(std::make_shared<output_string_adapter<CharType>>(s)) {}
4483
4484 operator output_adapter_t<CharType>()
4485 {
4486 return oa;
4487 }
4488
4489 private:
4490 output_adapter_t<CharType> oa = nullptr;
4491};
4492
4493//////////////////////////////
4494// binary reader and writer //
4495//////////////////////////////
4496
4497/*!
4498@brief deserialization of CBOR and MessagePack values
4499*/
4500template<typename BasicJsonType>
4501class binary_reader
4502{
4503 using number_integer_t = typename BasicJsonType::number_integer_t;
4504 using number_unsigned_t = typename BasicJsonType::number_unsigned_t;
4505
4506 public:
4507 /*!
4508 @brief create a binary reader
4509
4510 @param[in] adapter input adapter to read from
4511 */
4512 explicit binary_reader(input_adapter_t adapter) : ia(std::move(adapter))
4513 {
4514 assert(ia);
4515 }
4516
4517 /*!
4518 @brief create a JSON value from CBOR input
4519
4520 @param[in] strict whether to expect the input to be consumed completed
4521 @return JSON value created from CBOR input
4522
4523 @throw parse_error.110 if input ended unexpectedly or the end of file was
4524 not reached when @a strict was set to true
4525 @throw parse_error.112 if unsupported byte was read
4526 */
4527 BasicJsonType parse_cbor(const bool strict)
4528 {
4529 const auto res = parse_cbor_internal();
4530 if (strict)
4531 {
4532 get();
4533 check_eof(true);
4534 }
4535 return res;
4536 }
4537
4538 /*!
4539 @brief create a JSON value from MessagePack input
4540
4541 @param[in] strict whether to expect the input to be consumed completed
4542 @return JSON value created from MessagePack input
4543
4544 @throw parse_error.110 if input ended unexpectedly or the end of file was
4545 not reached when @a strict was set to true
4546 @throw parse_error.112 if unsupported byte was read
4547 */
4548 BasicJsonType parse_msgpack(const bool strict)
4549 {
4550 const auto res = parse_msgpack_internal();
4551 if (strict)
4552 {
4553 get();
4554 check_eof(true);
4555 }
4556 return res;
4557 }
4558
4559 /*!
4560 @brief determine system byte order
4561
4562 @return true if and only if system's byte order is little endian
4563
4564 @note from http://stackoverflow.com/a/1001328/266378
4565 */
4566 static constexpr bool little_endianess(int num = 1) noexcept
4567 {
4568 return (*reinterpret_cast<char*>(&num) == 1);
4569 }
4570
4571 private:
4572 /*!
4573 @param[in] get_char whether a new character should be retrieved from the
4574 input (true, default) or whether the last read
4575 character should be considered instead
4576 */
4577 BasicJsonType parse_cbor_internal(const bool get_char = true)
4578 {
4579 switch (get_char ? get() : current)
4580 {
4581 // EOF
4582 case std::char_traits<char>::eof():
4583 JSON_THROW(parse_error::create(110, chars_read, "unexpected end of input"));
4584
4585 // Integer 0x00..0x17 (0..23)
4586 case 0x00:
4587 case 0x01:
4588 case 0x02:
4589 case 0x03:
4590 case 0x04:
4591 case 0x05:
4592 case 0x06:
4593 case 0x07:
4594 case 0x08:
4595 case 0x09:
4596 case 0x0a:
4597 case 0x0b:
4598 case 0x0c:
4599 case 0x0d:
4600 case 0x0e:
4601 case 0x0f:
4602 case 0x10:
4603 case 0x11:
4604 case 0x12:
4605 case 0x13:
4606 case 0x14:
4607 case 0x15:
4608 case 0x16:
4609 case 0x17:
4610 return static_cast<number_unsigned_t>(current);
4611
4612 case 0x18: // Unsigned integer (one-byte uint8_t follows)
4613 return get_number<uint8_t>();
4614
4615 case 0x19: // Unsigned integer (two-byte uint16_t follows)
4616 return get_number<uint16_t>();
4617
4618 case 0x1a: // Unsigned integer (four-byte uint32_t follows)
4619 return get_number<uint32_t>();
4620
4621 case 0x1b: // Unsigned integer (eight-byte uint64_t follows)
4622 return get_number<uint64_t>();
4623
4624 // Negative integer -1-0x00..-1-0x17 (-1..-24)
4625 case 0x20:
4626 case 0x21:
4627 case 0x22:
4628 case 0x23:
4629 case 0x24:
4630 case 0x25:
4631 case 0x26:
4632 case 0x27:
4633 case 0x28:
4634 case 0x29:
4635 case 0x2a:
4636 case 0x2b:
4637 case 0x2c:
4638 case 0x2d:
4639 case 0x2e:
4640 case 0x2f:
4641 case 0x30:
4642 case 0x31:
4643 case 0x32:
4644 case 0x33:
4645 case 0x34:
4646 case 0x35:
4647 case 0x36:
4648 case 0x37:
4649 return static_cast<int8_t>(0x20 - 1 - current);
4650
4651 case 0x38: // Negative integer (one-byte uint8_t follows)
4652 {
4653 // must be uint8_t !
4654 return static_cast<number_integer_t>(-1) - get_number<uint8_t>();
4655 }
4656
4657 case 0x39: // Negative integer -1-n (two-byte uint16_t follows)
4658 {
4659 return static_cast<number_integer_t>(-1) - get_number<uint16_t>();
4660 }
4661
4662 case 0x3a: // Negative integer -1-n (four-byte uint32_t follows)
4663 {
4664 return static_cast<number_integer_t>(-1) - get_number<uint32_t>();
4665 }
4666
4667 case 0x3b: // Negative integer -1-n (eight-byte uint64_t follows)
4668 {
4669 return static_cast<number_integer_t>(-1) -
4670 static_cast<number_integer_t>(get_number<uint64_t>());
4671 }
4672
4673 // UTF-8 string (0x00..0x17 bytes follow)
4674 case 0x60:
4675 case 0x61:
4676 case 0x62:
4677 case 0x63:
4678 case 0x64:
4679 case 0x65:
4680 case 0x66:
4681 case 0x67:
4682 case 0x68:
4683 case 0x69:
4684 case 0x6a:
4685 case 0x6b:
4686 case 0x6c:
4687 case 0x6d:
4688 case 0x6e:
4689 case 0x6f:
4690 case 0x70:
4691 case 0x71:
4692 case 0x72:
4693 case 0x73:
4694 case 0x74:
4695 case 0x75:
4696 case 0x76:
4697 case 0x77:
4698 case 0x78: // UTF-8 string (one-byte uint8_t for n follows)
4699 case 0x79: // UTF-8 string (two-byte uint16_t for n follow)
4700 case 0x7a: // UTF-8 string (four-byte uint32_t for n follow)
4701 case 0x7b: // UTF-8 string (eight-byte uint64_t for n follow)
4702 case 0x7f: // UTF-8 string (indefinite length)
4703 {
4704 return get_cbor_string();
4705 }
4706
4707 // array (0x00..0x17 data items follow)
4708 case 0x80:
4709 case 0x81:
4710 case 0x82:
4711 case 0x83:
4712 case 0x84:
4713 case 0x85:
4714 case 0x86:
4715 case 0x87:
4716 case 0x88:
4717 case 0x89:
4718 case 0x8a:
4719 case 0x8b:
4720 case 0x8c:
4721 case 0x8d:
4722 case 0x8e:
4723 case 0x8f:
4724 case 0x90:
4725 case 0x91:
4726 case 0x92:
4727 case 0x93:
4728 case 0x94:
4729 case 0x95:
4730 case 0x96:
4731 case 0x97:
4732 {
4733 return get_cbor_array(current & 0x1f);
4734 }
4735
4736 case 0x98: // array (one-byte uint8_t for n follows)
4737 {
4738 return get_cbor_array(get_number<uint8_t>());
4739 }
4740
4741 case 0x99: // array (two-byte uint16_t for n follow)
4742 {
4743 return get_cbor_array(get_number<uint16_t>());
4744 }
4745
4746 case 0x9a: // array (four-byte uint32_t for n follow)
4747 {
4748 return get_cbor_array(get_number<uint32_t>());
4749 }
4750
4751 case 0x9b: // array (eight-byte uint64_t for n follow)
4752 {
4753 return get_cbor_array(get_number<uint64_t>());
4754 }
4755
4756 case 0x9f: // array (indefinite length)
4757 {
4758 BasicJsonType result = value_t::array;
4759 while (get() != 0xff)
4760 {
4761 result.push_back(parse_cbor_internal(false));
4762 }
4763 return result;
4764 }
4765
4766 // map (0x00..0x17 pairs of data items follow)
4767 case 0xa0:
4768 case 0xa1:
4769 case 0xa2:
4770 case 0xa3:
4771 case 0xa4:
4772 case 0xa5:
4773 case 0xa6:
4774 case 0xa7:
4775 case 0xa8:
4776 case 0xa9:
4777 case 0xaa:
4778 case 0xab:
4779 case 0xac:
4780 case 0xad:
4781 case 0xae:
4782 case 0xaf:
4783 case 0xb0:
4784 case 0xb1:
4785 case 0xb2:
4786 case 0xb3:
4787 case 0xb4:
4788 case 0xb5:
4789 case 0xb6:
4790 case 0xb7:
4791 {
4792 return get_cbor_object(current & 0x1f);
4793 }
4794
4795 case 0xb8: // map (one-byte uint8_t for n follows)
4796 {
4797 return get_cbor_object(get_number<uint8_t>());
4798 }
4799
4800 case 0xb9: // map (two-byte uint16_t for n follow)
4801 {
4802 return get_cbor_object(get_number<uint16_t>());
4803 }
4804
4805 case 0xba: // map (four-byte uint32_t for n follow)
4806 {
4807 return get_cbor_object(get_number<uint32_t>());
4808 }
4809
4810 case 0xbb: // map (eight-byte uint64_t for n follow)
4811 {
4812 return get_cbor_object(get_number<uint64_t>());
4813 }
4814
4815 case 0xbf: // map (indefinite length)
4816 {
4817 BasicJsonType result = value_t::object;
4818 while (get() != 0xff)
4819 {
4820 auto key = get_cbor_string();
4821 result[key] = parse_cbor_internal();
4822 }
4823 return result;
4824 }
4825
4826 case 0xf4: // false
4827 {
4828 return false;
4829 }
4830
4831 case 0xf5: // true
4832 {
4833 return true;
4834 }
4835
4836 case 0xf6: // null
4837 {
4838 return value_t::null;
4839 }
4840
4841 case 0xf9: // Half-Precision Float (two-byte IEEE 754)
4842 {
4843 const int byte1 = get();
4844 check_eof();
4845 const int byte2 = get();
4846 check_eof();
4847
4848 // code from RFC 7049, Appendix D, Figure 3:
4849 // As half-precision floating-point numbers were only added
4850 // to IEEE 754 in 2008, today's programming platforms often
4851 // still only have limited support for them. It is very
4852 // easy to include at least decoding support for them even
4853 // without such support. An example of a small decoder for
4854 // half-precision floating-point numbers in the C language
4855 // is shown in Fig. 3.
4856 const int half = (byte1 << 8) + byte2;
4857 const int exp = (half >> 10) & 0x1f;
4858 const int mant = half & 0x3ff;
4859 double val;
4860 if (exp == 0)
4861 {
4862 val = std::ldexp(mant, -24);
4863 }
4864 else if (exp != 31)
4865 {
4866 val = std::ldexp(mant + 1024, exp - 25);
4867 }
4868 else
4869 {
4870 val = (mant == 0) ? std::numeric_limits<double>::infinity()
4871 : std::numeric_limits<double>::quiet_NaN();
4872 }
4873 return (half & 0x8000) != 0 ? -val : val;
4874 }
4875
4876 case 0xfa: // Single-Precision Float (four-byte IEEE 754)
4877 {
4878 return get_number<float>();
4879 }
4880
4881 case 0xfb: // Double-Precision Float (eight-byte IEEE 754)
4882 {
4883 return get_number<double>();
4884 }
4885
4886 default: // anything else (0xFF is handled inside the other types)
4887 {
4888 std::stringstream ss;
4889 ss << std::setw(2) << std::setfill('0') << std::hex << current;
4890 JSON_THROW(parse_error::create(112, chars_read, "error reading CBOR; last byte: 0x" + ss.str()));
4891 }
4892 }
4893 }
4894
4895 BasicJsonType parse_msgpack_internal()
4896 {
4897 switch (get())
4898 {
4899 // EOF
4900 case std::char_traits<char>::eof():
4901 JSON_THROW(parse_error::create(110, chars_read, "unexpected end of input"));
4902
4903 // positive fixint
4904 case 0x00:
4905 case 0x01:
4906 case 0x02:
4907 case 0x03:
4908 case 0x04:
4909 case 0x05:
4910 case 0x06:
4911 case 0x07:
4912 case 0x08:
4913 case 0x09:
4914 case 0x0a:
4915 case 0x0b:
4916 case 0x0c:
4917 case 0x0d:
4918 case 0x0e:
4919 case 0x0f:
4920 case 0x10:
4921 case 0x11:
4922 case 0x12:
4923 case 0x13:
4924 case 0x14:
4925 case 0x15:
4926 case 0x16:
4927 case 0x17:
4928 case 0x18:
4929 case 0x19:
4930 case 0x1a:
4931 case 0x1b:
4932 case 0x1c:
4933 case 0x1d:
4934 case 0x1e:
4935 case 0x1f:
4936 case 0x20:
4937 case 0x21:
4938 case 0x22:
4939 case 0x23:
4940 case 0x24:
4941 case 0x25:
4942 case 0x26:
4943 case 0x27:
4944 case 0x28:
4945 case 0x29:
4946 case 0x2a:
4947 case 0x2b:
4948 case 0x2c:
4949 case 0x2d:
4950 case 0x2e:
4951 case 0x2f:
4952 case 0x30:
4953 case 0x31:
4954 case 0x32:
4955 case 0x33:
4956 case 0x34:
4957 case 0x35:
4958 case 0x36:
4959 case 0x37:
4960 case 0x38:
4961 case 0x39:
4962 case 0x3a:
4963 case 0x3b:
4964 case 0x3c:
4965 case 0x3d:
4966 case 0x3e:
4967 case 0x3f:
4968 case 0x40:
4969 case 0x41:
4970 case 0x42:
4971 case 0x43:
4972 case 0x44:
4973 case 0x45:
4974 case 0x46:
4975 case 0x47:
4976 case 0x48:
4977 case 0x49:
4978 case 0x4a:
4979 case 0x4b:
4980 case 0x4c:
4981 case 0x4d:
4982 case 0x4e:
4983 case 0x4f:
4984 case 0x50:
4985 case 0x51:
4986 case 0x52:
4987 case 0x53:
4988 case 0x54:
4989 case 0x55:
4990 case 0x56:
4991 case 0x57:
4992 case 0x58:
4993 case 0x59:
4994 case 0x5a:
4995 case 0x5b:
4996 case 0x5c:
4997 case 0x5d:
4998 case 0x5e:
4999 case 0x5f:
5000 case 0x60:
5001 case 0x61:
5002 case 0x62:
5003 case 0x63:
5004 case 0x64:
5005 case 0x65:
5006 case 0x66:
5007 case 0x67:
5008 case 0x68:
5009 case 0x69:
5010 case 0x6a:
5011 case 0x6b:
5012 case 0x6c:
5013 case 0x6d:
5014 case 0x6e:
5015 case 0x6f:
5016 case 0x70:
5017 case 0x71:
5018 case 0x72:
5019 case 0x73:
5020 case 0x74:
5021 case 0x75:
5022 case 0x76:
5023 case 0x77:
5024 case 0x78:
5025 case 0x79:
5026 case 0x7a:
5027 case 0x7b:
5028 case 0x7c:
5029 case 0x7d:
5030 case 0x7e:
5031 case 0x7f:
5032 return static_cast<number_unsigned_t>(current);
5033
5034 // fixmap
5035 case 0x80:
5036 case 0x81:
5037 case 0x82:
5038 case 0x83:
5039 case 0x84:
5040 case 0x85:
5041 case 0x86:
5042 case 0x87:
5043 case 0x88:
5044 case 0x89:
5045 case 0x8a:
5046 case 0x8b:
5047 case 0x8c:
5048 case 0x8d:
5049 case 0x8e:
5050 case 0x8f:
5051 {
5052 return get_msgpack_object(current & 0x0f);
5053 }
5054
5055 // fixarray
5056 case 0x90:
5057 case 0x91:
5058 case 0x92:
5059 case 0x93:
5060 case 0x94:
5061 case 0x95:
5062 case 0x96:
5063 case 0x97:
5064 case 0x98:
5065 case 0x99:
5066 case 0x9a:
5067 case 0x9b:
5068 case 0x9c:
5069 case 0x9d:
5070 case 0x9e:
5071 case 0x9f:
5072 {
5073 return get_msgpack_array(current & 0x0f);
5074 }
5075
5076 // fixstr
5077 case 0xa0:
5078 case 0xa1:
5079 case 0xa2:
5080 case 0xa3:
5081 case 0xa4:
5082 case 0xa5:
5083 case 0xa6:
5084 case 0xa7:
5085 case 0xa8:
5086 case 0xa9:
5087 case 0xaa:
5088 case 0xab:
5089 case 0xac:
5090 case 0xad:
5091 case 0xae:
5092 case 0xaf:
5093 case 0xb0:
5094 case 0xb1:
5095 case 0xb2:
5096 case 0xb3:
5097 case 0xb4:
5098 case 0xb5:
5099 case 0xb6:
5100 case 0xb7:
5101 case 0xb8:
5102 case 0xb9:
5103 case 0xba:
5104 case 0xbb:
5105 case 0xbc:
5106 case 0xbd:
5107 case 0xbe:
5108 case 0xbf:
5109 return get_msgpack_string();
5110
5111 case 0xc0: // nil
5112 return value_t::null;
5113
5114 case 0xc2: // false
5115 return false;
5116
5117 case 0xc3: // true
5118 return true;
5119
5120 case 0xca: // float 32
5121 return get_number<float>();
5122
5123 case 0xcb: // float 64
5124 return get_number<double>();
5125
5126 case 0xcc: // uint 8
5127 return get_number<uint8_t>();
5128
5129 case 0xcd: // uint 16
5130 return get_number<uint16_t>();
5131
5132 case 0xce: // uint 32
5133 return get_number<uint32_t>();
5134
5135 case 0xcf: // uint 64
5136 return get_number<uint64_t>();
5137
5138 case 0xd0: // int 8
5139 return get_number<int8_t>();
5140
5141 case 0xd1: // int 16
5142 return get_number<int16_t>();
5143
5144 case 0xd2: // int 32
5145 return get_number<int32_t>();
5146
5147 case 0xd3: // int 64
5148 return get_number<int64_t>();
5149
5150 case 0xd9: // str 8
5151 case 0xda: // str 16
5152 case 0xdb: // str 32
5153 return get_msgpack_string();
5154
5155 case 0xdc: // array 16
5156 {
5157 return get_msgpack_array(get_number<uint16_t>());
5158 }
5159
5160 case 0xdd: // array 32
5161 {
5162 return get_msgpack_array(get_number<uint32_t>());
5163 }
5164
5165 case 0xde: // map 16
5166 {
5167 return get_msgpack_object(get_number<uint16_t>());
5168 }
5169
5170 case 0xdf: // map 32
5171 {
5172 return get_msgpack_object(get_number<uint32_t>());
5173 }
5174
5175 // positive fixint
5176 case 0xe0:
5177 case 0xe1:
5178 case 0xe2:
5179 case 0xe3:
5180 case 0xe4:
5181 case 0xe5:
5182 case 0xe6:
5183 case 0xe7:
5184 case 0xe8:
5185 case 0xe9:
5186 case 0xea:
5187 case 0xeb:
5188 case 0xec:
5189 case 0xed:
5190 case 0xee:
5191 case 0xef:
5192 case 0xf0:
5193 case 0xf1:
5194 case 0xf2:
5195 case 0xf3:
5196 case 0xf4:
5197 case 0xf5:
5198 case 0xf6:
5199 case 0xf7:
5200 case 0xf8:
5201 case 0xf9:
5202 case 0xfa:
5203 case 0xfb:
5204 case 0xfc:
5205 case 0xfd:
5206 case 0xfe:
5207 case 0xff:
5208 return static_cast<int8_t>(current);
5209
5210 default: // anything else
5211 {
5212 std::stringstream ss;
5213 ss << std::setw(2) << std::setfill('0') << std::hex << current;
5214 JSON_THROW(parse_error::create(112, chars_read,
5215 "error reading MessagePack; last byte: 0x" + ss.str()));
5216 }
5217 }
5218 }
5219
5220 /*!
5221 @brief get next character from the input
5222
5223 This function provides the interface to the used input adapter. It does
5224 not throw in case the input reached EOF, but returns
5225 `std::char_traits<char>::eof()` in that case.
5226
5227 @return character read from the input
5228 */
5229 int get()
5230 {
5231 ++chars_read;
5232 return (current = ia->get_character());
5233 }
5234
5235 /*
5236 @brief read a number from the input
5237
5238 @tparam NumberType the type of the number
5239
5240 @return number of type @a NumberType
5241
5242 @note This function needs to respect the system's endianess, because
5243 bytes in CBOR and MessagePack are stored in network order (big
5244 endian) and therefore need reordering on little endian systems.
5245
5246 @throw parse_error.110 if input has less than `sizeof(NumberType)` bytes
5247 */
5248 template<typename NumberType> NumberType get_number()
5249 {
5250 // step 1: read input into array with system's byte order
5251 std::array<uint8_t, sizeof(NumberType)> vec;
5252 for (std::size_t i = 0; i < sizeof(NumberType); ++i)
5253 {
5254 get();
5255 check_eof();
5256
5257 // reverse byte order prior to conversion if necessary
5258 if (is_little_endian)
5259 {
5260 vec[sizeof(NumberType) - i - 1] = static_cast<uint8_t>(current);
5261 }
5262 else
5263 {
5264 vec[i] = static_cast<uint8_t>(current); // LCOV_EXCL_LINE
5265 }
5266 }
5267
5268 // step 2: convert array into number of type T and return
5269 NumberType result;
5270 std::memcpy(&result, vec.data(), sizeof(NumberType));
5271 return result;
5272 }
5273
5274 /*!
5275 @brief create a string by reading characters from the input
5276
5277 @param[in] len number of bytes to read
5278
5279 @note We can not reserve @a len bytes for the result, because @a len
5280 may be too large. Usually, @ref check_eof() detects the end of
5281 the input before we run out of string memory.
5282
5283 @return string created by reading @a len bytes
5284
5285 @throw parse_error.110 if input has less than @a len bytes
5286 */
5287 template<typename NumberType>
5288 std::string get_string(const NumberType len)
5289 {
5290 std::string result;
5291 std::generate_n(std::back_inserter(result), len, [this]()
5292 {
5293 get();
5294 check_eof();
5295 return static_cast<char>(current);
5296 });
5297 return result;
5298 }
5299
5300 /*!
5301 @brief reads a CBOR string
5302
5303 This function first reads starting bytes to determine the expected
5304 string length and then copies this number of bytes into a string.
5305 Additionally, CBOR's strings with indefinite lengths are supported.
5306
5307 @return string
5308
5309 @throw parse_error.110 if input ended
5310 @throw parse_error.113 if an unexpected byte is read
5311 */
5312 std::string get_cbor_string()
5313 {
5314 check_eof();
5315
5316 switch (current)
5317 {
5318 // UTF-8 string (0x00..0x17 bytes follow)
5319 case 0x60:
5320 case 0x61:
5321 case 0x62:
5322 case 0x63:
5323 case 0x64:
5324 case 0x65:
5325 case 0x66:
5326 case 0x67:
5327 case 0x68:
5328 case 0x69:
5329 case 0x6a:
5330 case 0x6b:
5331 case 0x6c:
5332 case 0x6d:
5333 case 0x6e:
5334 case 0x6f:
5335 case 0x70:
5336 case 0x71:
5337 case 0x72:
5338 case 0x73:
5339 case 0x74:
5340 case 0x75:
5341 case 0x76:
5342 case 0x77:
5343 {
5344 return get_string(current & 0x1f);
5345 }
5346
5347 case 0x78: // UTF-8 string (one-byte uint8_t for n follows)
5348 {
5349 return get_string(get_number<uint8_t>());
5350 }
5351
5352 case 0x79: // UTF-8 string (two-byte uint16_t for n follow)
5353 {
5354 return get_string(get_number<uint16_t>());
5355 }
5356
5357 case 0x7a: // UTF-8 string (four-byte uint32_t for n follow)
5358 {
5359 return get_string(get_number<uint32_t>());
5360 }
5361
5362 case 0x7b: // UTF-8 string (eight-byte uint64_t for n follow)
5363 {
5364 return get_string(get_number<uint64_t>());
5365 }
5366
5367 case 0x7f: // UTF-8 string (indefinite length)
5368 {
5369 std::string result;
5370 while (get() != 0xff)
5371 {
5372 check_eof();
5373 result.push_back(static_cast<char>(current));
5374 }
5375 return result;
5376 }
5377
5378 default:
5379 {
5380 std::stringstream ss;
5381 ss << std::setw(2) << std::setfill('0') << std::hex << current;
5382 JSON_THROW(parse_error::create(113, chars_read, "expected a CBOR string; last byte: 0x" + ss.str()));
5383 }
5384 }
5385 }
5386
5387 template<typename NumberType>
5388 BasicJsonType get_cbor_array(const NumberType len)
5389 {
5390 BasicJsonType result = value_t::array;
5391 std::generate_n(std::back_inserter(*result.m_value.array), len, [this]()
5392 {
5393 return parse_cbor_internal();
5394 });
5395 return result;
5396 }
5397
5398 template<typename NumberType>
5399 BasicJsonType get_cbor_object(const NumberType len)
5400 {
5401 BasicJsonType result = value_t::object;
5402 std::generate_n(std::inserter(*result.m_value.object,
5403 result.m_value.object->end()),
5404 len, [this]()
5405 {
5406 get();
5407 auto key = get_cbor_string();
5408 auto val = parse_cbor_internal();
5409 return std::make_pair(std::move(key), std::move(val));
5410 });
5411 return result;
5412 }
5413
5414 /*!
5415 @brief reads a MessagePack string
5416
5417 This function first reads starting bytes to determine the expected
5418 string length and then copies this number of bytes into a string.
5419
5420 @return string
5421
5422 @throw parse_error.110 if input ended
5423 @throw parse_error.113 if an unexpected byte is read
5424 */
5425 std::string get_msgpack_string()
5426 {
5427 check_eof();
5428
5429 switch (current)
5430 {
5431 // fixstr
5432 case 0xa0:
5433 case 0xa1:
5434 case 0xa2:
5435 case 0xa3:
5436 case 0xa4:
5437 case 0xa5:
5438 case 0xa6:
5439 case 0xa7:
5440 case 0xa8:
5441 case 0xa9:
5442 case 0xaa:
5443 case 0xab:
5444 case 0xac:
5445 case 0xad:
5446 case 0xae:
5447 case 0xaf:
5448 case 0xb0:
5449 case 0xb1:
5450 case 0xb2:
5451 case 0xb3:
5452 case 0xb4:
5453 case 0xb5:
5454 case 0xb6:
5455 case 0xb7:
5456 case 0xb8:
5457 case 0xb9:
5458 case 0xba:
5459 case 0xbb:
5460 case 0xbc:
5461 case 0xbd:
5462 case 0xbe:
5463 case 0xbf:
5464 {
5465 return get_string(current & 0x1f);
5466 }
5467
5468 case 0xd9: // str 8
5469 {
5470 return get_string(get_number<uint8_t>());
5471 }
5472
5473 case 0xda: // str 16
5474 {
5475 return get_string(get_number<uint16_t>());
5476 }
5477
5478 case 0xdb: // str 32
5479 {
5480 return get_string(get_number<uint32_t>());
5481 }
5482
5483 default:
5484 {
5485 std::stringstream ss;
5486 ss << std::setw(2) << std::setfill('0') << std::hex << current;
5487 JSON_THROW(parse_error::create(113, chars_read,
5488 "expected a MessagePack string; last byte: 0x" + ss.str()));
5489 }
5490 }
5491 }
5492
5493 template<typename NumberType>
5494 BasicJsonType get_msgpack_array(const NumberType len)
5495 {
5496 BasicJsonType result = value_t::array;
5497 std::generate_n(std::back_inserter(*result.m_value.array), len, [this]()
5498 {
5499 return parse_msgpack_internal();
5500 });
5501 return result;
5502 }
5503
5504 template<typename NumberType>
5505 BasicJsonType get_msgpack_object(const NumberType len)
5506 {
5507 BasicJsonType result = value_t::object;
5508 std::generate_n(std::inserter(*result.m_value.object,
5509 result.m_value.object->end()),
5510 len, [this]()
5511 {
5512 get();
5513 auto key = get_msgpack_string();
5514 auto val = parse_msgpack_internal();
5515 return std::make_pair(std::move(key), std::move(val));
5516 });
5517 return result;
5518 }
5519
5520 /*!
5521 @brief check if input ended
5522 @throw parse_error.110 if input ended
5523 */
5524 void check_eof(const bool expect_eof = false) const
5525 {
5526 if (expect_eof)
5527 {
5528 if (JSON_UNLIKELY(current != std::char_traits<char>::eof()))
5529 {
5530 JSON_THROW(parse_error::create(110, chars_read, "expected end of input"));
5531 }
5532 }
5533 else
5534 {
5535 if (JSON_UNLIKELY(current == std::char_traits<char>::eof()))
5536 {
5537 JSON_THROW(parse_error::create(110, chars_read, "unexpected end of input"));
5538 }
5539 }
5540 }
5541
5542 private:
5543 /// input adapter
5544 input_adapter_t ia = nullptr;
5545
5546 /// the current character
5547 int current = std::char_traits<char>::eof();
5548
5549 /// the number of characters read
5550 std::size_t chars_read = 0;
5551
5552 /// whether we can assume little endianess
5553 const bool is_little_endian = little_endianess();
5554};
5555
5556/*!
5557@brief serialization to CBOR and MessagePack values
5558*/
5559template<typename BasicJsonType, typename CharType>
5560class binary_writer
5561{
5562 public:
5563 /*!
5564 @brief create a binary writer
5565
5566 @param[in] adapter output adapter to write to
5567 */
5568 explicit binary_writer(output_adapter_t<CharType> adapter) : oa(adapter)
5569 {
5570 assert(oa);
5571 }
5572
5573 /*!
5574 @brief[in] j JSON value to serialize
5575 */
5576 void write_cbor(const BasicJsonType& j)
5577 {
5578 switch (j.type())
5579 {
5580 case value_t::null:
5581 {
5582 oa->write_character(static_cast<CharType>(0xf6));
5583 break;
5584 }
5585
5586 case value_t::boolean:
5587 {
5588 oa->write_character(j.m_value.boolean
5589 ? static_cast<CharType>(0xf5)
5590 : static_cast<CharType>(0xf4));
5591 break;
5592 }
5593
5594 case value_t::number_integer:
5595 {
5596 if (j.m_value.number_integer >= 0)
5597 {
5598 // CBOR does not differentiate between positive signed
5599 // integers and unsigned integers. Therefore, we used the
5600 // code from the value_t::number_unsigned case here.
5601 if (j.m_value.number_integer <= 0x17)
5602 {
5603 write_number(static_cast<uint8_t>(j.m_value.number_integer));
5604 }
5605 else if (j.m_value.number_integer <= (std::numeric_limits<uint8_t>::max)())
5606 {
5607 oa->write_character(static_cast<CharType>(0x18));
5608 write_number(static_cast<uint8_t>(j.m_value.number_integer));
5609 }
5610 else if (j.m_value.number_integer <= (std::numeric_limits<uint16_t>::max)())
5611 {
5612 oa->write_character(static_cast<CharType>(0x19));
5613 write_number(static_cast<uint16_t>(j.m_value.number_integer));
5614 }
5615 else if (j.m_value.number_integer <= (std::numeric_limits<uint32_t>::max)())
5616 {
5617 oa->write_character(static_cast<CharType>(0x1a));
5618 write_number(static_cast<uint32_t>(j.m_value.number_integer));
5619 }
5620 else
5621 {
5622 oa->write_character(static_cast<CharType>(0x1b));
5623 write_number(static_cast<uint64_t>(j.m_value.number_integer));
5624 }
5625 }
5626 else
5627 {
5628 // The conversions below encode the sign in the first
5629 // byte, and the value is converted to a positive number.
5630 const auto positive_number = -1 - j.m_value.number_integer;
5631 if (j.m_value.number_integer >= -24)
5632 {
5633 write_number(static_cast<uint8_t>(0x20 + positive_number));
5634 }
5635 else if (positive_number <= (std::numeric_limits<uint8_t>::max)())
5636 {
5637 oa->write_character(static_cast<CharType>(0x38));
5638 write_number(static_cast<uint8_t>(positive_number));
5639 }
5640 else if (positive_number <= (std::numeric_limits<uint16_t>::max)())
5641 {
5642 oa->write_character(static_cast<CharType>(0x39));
5643 write_number(static_cast<uint16_t>(positive_number));
5644 }
5645 else if (positive_number <= (std::numeric_limits<uint32_t>::max)())
5646 {
5647 oa->write_character(static_cast<CharType>(0x3a));
5648 write_number(static_cast<uint32_t>(positive_number));
5649 }
5650 else
5651 {
5652 oa->write_character(static_cast<CharType>(0x3b));
5653 write_number(static_cast<uint64_t>(positive_number));
5654 }
5655 }
5656 break;
5657 }
5658
5659 case value_t::number_unsigned:
5660 {
5661 if (j.m_value.number_unsigned <= 0x17)
5662 {
5663 write_number(static_cast<uint8_t>(j.m_value.number_unsigned));
5664 }
5665 else if (j.m_value.number_unsigned <= (std::numeric_limits<uint8_t>::max)())
5666 {
5667 oa->write_character(static_cast<CharType>(0x18));
5668 write_number(static_cast<uint8_t>(j.m_value.number_unsigned));
5669 }
5670 else if (j.m_value.number_unsigned <= (std::numeric_limits<uint16_t>::max)())
5671 {
5672 oa->write_character(static_cast<CharType>(0x19));
5673 write_number(static_cast<uint16_t>(j.m_value.number_unsigned));
5674 }
5675 else if (j.m_value.number_unsigned <= (std::numeric_limits<uint32_t>::max)())
5676 {
5677 oa->write_character(static_cast<CharType>(0x1a));
5678 write_number(static_cast<uint32_t>(j.m_value.number_unsigned));
5679 }
5680 else
5681 {
5682 oa->write_character(static_cast<CharType>(0x1b));
5683 write_number(static_cast<uint64_t>(j.m_value.number_unsigned));
5684 }
5685 break;
5686 }
5687
5688 case value_t::number_float: // Double-Precision Float
5689 {
5690 oa->write_character(static_cast<CharType>(0xfb));
5691 write_number(j.m_value.number_float);
5692 break;
5693 }
5694
5695 case value_t::string:
5696 {
5697 // step 1: write control byte and the string length
5698 const auto N = j.m_value.string->size();
5699 if (N <= 0x17)
5700 {
5701 write_number(static_cast<uint8_t>(0x60 + N));
5702 }
5703 else if (N <= 0xff)
5704 {
5705 oa->write_character(static_cast<CharType>(0x78));
5706 write_number(static_cast<uint8_t>(N));
5707 }
5708 else if (N <= 0xffff)
5709 {
5710 oa->write_character(static_cast<CharType>(0x79));
5711 write_number(static_cast<uint16_t>(N));
5712 }
5713 else if (N <= 0xffffffff)
5714 {
5715 oa->write_character(static_cast<CharType>(0x7a));
5716 write_number(static_cast<uint32_t>(N));
5717 }
5718 // LCOV_EXCL_START
5719 else if (N <= 0xffffffffffffffff)
5720 {
5721 oa->write_character(static_cast<CharType>(0x7b));
5722 write_number(static_cast<uint64_t>(N));
5723 }
5724 // LCOV_EXCL_STOP
5725
5726 // step 2: write the string
5727 oa->write_characters(
5728 reinterpret_cast<const CharType*>(j.m_value.string->c_str()),
5729 j.m_value.string->size());
5730 break;
5731 }
5732
5733 case value_t::array:
5734 {
5735 // step 1: write control byte and the array size
5736 const auto N = j.m_value.array->size();
5737 if (N <= 0x17)
5738 {
5739 write_number(static_cast<uint8_t>(0x80 + N));
5740 }
5741 else if (N <= 0xff)
5742 {
5743 oa->write_character(static_cast<CharType>(0x98));
5744 write_number(static_cast<uint8_t>(N));
5745 }
5746 else if (N <= 0xffff)
5747 {
5748 oa->write_character(static_cast<CharType>(0x99));
5749 write_number(static_cast<uint16_t>(N));
5750 }
5751 else if (N <= 0xffffffff)
5752 {
5753 oa->write_character(static_cast<CharType>(0x9a));
5754 write_number(static_cast<uint32_t>(N));
5755 }
5756 // LCOV_EXCL_START
5757 else if (N <= 0xffffffffffffffff)
5758 {
5759 oa->write_character(static_cast<CharType>(0x9b));
5760 write_number(static_cast<uint64_t>(N));
5761 }
5762 // LCOV_EXCL_STOP
5763
5764 // step 2: write each element
5765 for (const auto& el : *j.m_value.array)
5766 {
5767 write_cbor(el);
5768 }
5769 break;
5770 }
5771
5772 case value_t::object:
5773 {
5774 // step 1: write control byte and the object size
5775 const auto N = j.m_value.object->size();
5776 if (N <= 0x17)
5777 {
5778 write_number(static_cast<uint8_t>(0xa0 + N));
5779 }
5780 else if (N <= 0xff)
5781 {
5782 oa->write_character(static_cast<CharType>(0xb8));
5783 write_number(static_cast<uint8_t>(N));
5784 }
5785 else if (N <= 0xffff)
5786 {
5787 oa->write_character(static_cast<CharType>(0xb9));
5788 write_number(static_cast<uint16_t>(N));
5789 }
5790 else if (N <= 0xffffffff)
5791 {
5792 oa->write_character(static_cast<CharType>(0xba));
5793 write_number(static_cast<uint32_t>(N));
5794 }
5795 // LCOV_EXCL_START
5796 else if (N <= 0xffffffffffffffff)
5797 {
5798 oa->write_character(static_cast<CharType>(0xbb));
5799 write_number(static_cast<uint64_t>(N));
5800 }
5801 // LCOV_EXCL_STOP
5802
5803 // step 2: write each element
5804 for (const auto& el : *j.m_value.object)
5805 {
5806 write_cbor(el.first);
5807 write_cbor(el.second);
5808 }
5809 break;
5810 }
5811
5812 default:
5813 break;
5814 }
5815 }
5816
5817 /*!
5818 @brief[in] j JSON value to serialize
5819 */
5820 void write_msgpack(const BasicJsonType& j)
5821 {
5822 switch (j.type())
5823 {
5824 case value_t::null: // nil
5825 {
5826 oa->write_character(static_cast<CharType>(0xc0));
5827 break;
5828 }
5829
5830 case value_t::boolean: // true and false
5831 {
5832 oa->write_character(j.m_value.boolean
5833 ? static_cast<CharType>(0xc3)
5834 : static_cast<CharType>(0xc2));
5835 break;
5836 }
5837
5838 case value_t::number_integer:
5839 {
5840 if (j.m_value.number_integer >= 0)
5841 {
5842 // MessagePack does not differentiate between positive
5843 // signed integers and unsigned integers. Therefore, we used
5844 // the code from the value_t::number_unsigned case here.
5845 if (j.m_value.number_unsigned < 128)
5846 {
5847 // positive fixnum
5848 write_number(static_cast<uint8_t>(j.m_value.number_integer));
5849 }
5850 else if (j.m_value.number_unsigned <= (std::numeric_limits<uint8_t>::max)())
5851 {
5852 // uint 8
5853 oa->write_character(static_cast<CharType>(0xcc));
5854 write_number(static_cast<uint8_t>(j.m_value.number_integer));
5855 }
5856 else if (j.m_value.number_unsigned <= (std::numeric_limits<uint16_t>::max)())
5857 {
5858 // uint 16
5859 oa->write_character(static_cast<CharType>(0xcd));
5860 write_number(static_cast<uint16_t>(j.m_value.number_integer));
5861 }
5862 else if (j.m_value.number_unsigned <= (std::numeric_limits<uint32_t>::max)())
5863 {
5864 // uint 32
5865 oa->write_character(static_cast<CharType>(0xce));
5866 write_number(static_cast<uint32_t>(j.m_value.number_integer));
5867 }
5868 else if (j.m_value.number_unsigned <= (std::numeric_limits<uint64_t>::max)())
5869 {
5870 // uint 64
5871 oa->write_character(static_cast<CharType>(0xcf));
5872 write_number(static_cast<uint64_t>(j.m_value.number_integer));
5873 }
5874 }
5875 else
5876 {
5877 if (j.m_value.number_integer >= -32)
5878 {
5879 // negative fixnum
5880 write_number(static_cast<int8_t>(j.m_value.number_integer));
5881 }
5882 else if (j.m_value.number_integer >= (std::numeric_limits<int8_t>::min)() and
5883 j.m_value.number_integer <= (std::numeric_limits<int8_t>::max)())
5884 {
5885 // int 8
5886 oa->write_character(static_cast<CharType>(0xd0));
5887 write_number(static_cast<int8_t>(j.m_value.number_integer));
5888 }
5889 else if (j.m_value.number_integer >= (std::numeric_limits<int16_t>::min)() and
5890 j.m_value.number_integer <= (std::numeric_limits<int16_t>::max)())
5891 {
5892 // int 16
5893 oa->write_character(static_cast<CharType>(0xd1));
5894 write_number(static_cast<int16_t>(j.m_value.number_integer));
5895 }
5896 else if (j.m_value.number_integer >= (std::numeric_limits<int32_t>::min)() and
5897 j.m_value.number_integer <= (std::numeric_limits<int32_t>::max)())
5898 {
5899 // int 32
5900 oa->write_character(static_cast<CharType>(0xd2));
5901 write_number(static_cast<int32_t>(j.m_value.number_integer));
5902 }
5903 else if (j.m_value.number_integer >= (std::numeric_limits<int64_t>::min)() and
5904 j.m_value.number_integer <= (std::numeric_limits<int64_t>::max)())
5905 {
5906 // int 64
5907 oa->write_character(static_cast<CharType>(0xd3));
5908 write_number(static_cast<int64_t>(j.m_value.number_integer));
5909 }
5910 }
5911 break;
5912 }
5913
5914 case value_t::number_unsigned:
5915 {
5916 if (j.m_value.number_unsigned < 128)
5917 {
5918 // positive fixnum
5919 write_number(static_cast<uint8_t>(j.m_value.number_integer));
5920 }
5921 else if (j.m_value.number_unsigned <= (std::numeric_limits<uint8_t>::max)())
5922 {
5923 // uint 8
5924 oa->write_character(static_cast<CharType>(0xcc));
5925 write_number(static_cast<uint8_t>(j.m_value.number_integer));
5926 }
5927 else if (j.m_value.number_unsigned <= (std::numeric_limits<uint16_t>::max)())
5928 {
5929 // uint 16
5930 oa->write_character(static_cast<CharType>(0xcd));
5931 write_number(static_cast<uint16_t>(j.m_value.number_integer));
5932 }
5933 else if (j.m_value.number_unsigned <= (std::numeric_limits<uint32_t>::max)())
5934 {
5935 // uint 32
5936 oa->write_character(static_cast<CharType>(0xce));
5937 write_number(static_cast<uint32_t>(j.m_value.number_integer));
5938 }
5939 else if (j.m_value.number_unsigned <= (std::numeric_limits<uint64_t>::max)())
5940 {
5941 // uint 64
5942 oa->write_character(static_cast<CharType>(0xcf));
5943 write_number(static_cast<uint64_t>(j.m_value.number_integer));
5944 }
5945 break;
5946 }
5947
5948 case value_t::number_float: // float 64
5949 {
5950 oa->write_character(static_cast<CharType>(0xcb));
5951 write_number(j.m_value.number_float);
5952 break;
5953 }
5954
5955 case value_t::string:
5956 {
5957 // step 1: write control byte and the string length
5958 const auto N = j.m_value.string->size();
5959 if (N <= 31)
5960 {
5961 // fixstr
5962 write_number(static_cast<uint8_t>(0xa0 | N));
5963 }
5964 else if (N <= 255)
5965 {
5966 // str 8
5967 oa->write_character(static_cast<CharType>(0xd9));
5968 write_number(static_cast<uint8_t>(N));
5969 }
5970 else if (N <= 65535)
5971 {
5972 // str 16
5973 oa->write_character(static_cast<CharType>(0xda));
5974 write_number(static_cast<uint16_t>(N));
5975 }
5976 else if (N <= 4294967295)
5977 {
5978 // str 32
5979 oa->write_character(static_cast<CharType>(0xdb));
5980 write_number(static_cast<uint32_t>(N));
5981 }
5982
5983 // step 2: write the string
5984 oa->write_characters(
5985 reinterpret_cast<const CharType*>(j.m_value.string->c_str()),
5986 j.m_value.string->size());
5987 break;
5988 }
5989
5990 case value_t::array:
5991 {
5992 // step 1: write control byte and the array size
5993 const auto N = j.m_value.array->size();
5994 if (N <= 15)
5995 {
5996 // fixarray
5997 write_number(static_cast<uint8_t>(0x90 | N));
5998 }
5999 else if (N <= 0xffff)
6000 {
6001 // array 16
6002 oa->write_character(static_cast<CharType>(0xdc));
6003 write_number(static_cast<uint16_t>(N));
6004 }
6005 else if (N <= 0xffffffff)
6006 {
6007 // array 32
6008 oa->write_character(static_cast<CharType>(0xdd));
6009 write_number(static_cast<uint32_t>(N));
6010 }
6011
6012 // step 2: write each element
6013 for (const auto& el : *j.m_value.array)
6014 {
6015 write_msgpack(el);
6016 }
6017 break;
6018 }
6019
6020 case value_t::object:
6021 {
6022 // step 1: write control byte and the object size
6023 const auto N = j.m_value.object->size();
6024 if (N <= 15)
6025 {
6026 // fixmap
6027 write_number(static_cast<uint8_t>(0x80 | (N & 0xf)));
6028 }
6029 else if (N <= 65535)
6030 {
6031 // map 16
6032 oa->write_character(static_cast<CharType>(0xde));
6033 write_number(static_cast<uint16_t>(N));
6034 }
6035 else if (N <= 4294967295)
6036 {
6037 // map 32
6038 oa->write_character(static_cast<CharType>(0xdf));
6039 write_number(static_cast<uint32_t>(N));
6040 }
6041
6042 // step 2: write each element
6043 for (const auto& el : *j.m_value.object)
6044 {
6045 write_msgpack(el.first);
6046 write_msgpack(el.second);
6047 }
6048 break;
6049 }
6050
6051 default:
6052 break;
6053 }
6054 }
6055
6056 private:
6057 /*
6058 @brief write a number to output input
6059
6060 @param[in] n number of type @a NumberType
6061 @tparam NumberType the type of the number
6062
6063 @note This function needs to respect the system's endianess, because bytes
6064 in CBOR and MessagePack are stored in network order (big endian) and
6065 therefore need reordering on little endian systems.
6066 */
6067 template<typename NumberType> void write_number(NumberType n)
6068 {
6069 // step 1: write number to array of length NumberType
6070 std::array<CharType, sizeof(NumberType)> vec;
6071 std::memcpy(vec.data(), &n, sizeof(NumberType));
6072
6073 // step 2: write array to output (with possible reordering)
6074 if (is_little_endian)
6075 {
6076 // reverse byte order prior to conversion if necessary
6077 std::reverse(vec.begin(), vec.end());
6078 }
6079
6080 oa->write_characters(vec.data(), sizeof(NumberType));
6081 }
6082
6083 private:
6084 /// whether we can assume little endianess
6085 const bool is_little_endian = binary_reader<BasicJsonType>::little_endianess();
6086
6087 /// the output
6088 output_adapter_t<CharType> oa = nullptr;
6089};
6090
6091///////////////////
6092// serialization //
6093///////////////////
6094
6095template<typename BasicJsonType>
6096class serializer
6097{
6098 using string_t = typename BasicJsonType::string_t;
6099 using number_float_t = typename BasicJsonType::number_float_t;
6100 using number_integer_t = typename BasicJsonType::number_integer_t;
6101 using number_unsigned_t = typename BasicJsonType::number_unsigned_t;
6102 public:
6103 /*!
6104 @param[in] s output stream to serialize to
6105 @param[in] ichar indentation character to use
6106 */
6107 serializer(output_adapter_t<char> s, const char ichar)
6108 : o(std::move(s)), loc(std::localeconv()),
6109 thousands_sep(loc->thousands_sep == nullptr ? '\0' : loc->thousands_sep[0]),
6110 decimal_point(loc->decimal_point == nullptr ? '\0' : loc->decimal_point[0]),
6111 indent_char(ichar), indent_string(512, indent_char) {}
6112
6113 // delete because of pointer members
6114 serializer(const serializer&) = delete;
6115 serializer& operator=(const serializer&) = delete;
6116
6117 /*!
6118 @brief internal implementation of the serialization function
6119
6120 This function is called by the public member function dump and organizes
6121 the serialization internally. The indentation level is propagated as
6122 additional parameter. In case of arrays and objects, the function is
6123 called recursively.
6124
6125 - strings and object keys are escaped using `escape_string()`
6126 - integer numbers are converted implicitly via `operator<<`
6127 - floating-point numbers are converted to a string using `"%g"` format
6128
6129 @param[in] val value to serialize
6130 @param[in] pretty_print whether the output shall be pretty-printed
6131 @param[in] indent_step the indent level
6132 @param[in] current_indent the current indent level (only used internally)
6133 */
6134 void dump(const BasicJsonType& val, const bool pretty_print,
6135 const bool ensure_ascii,
6136 const unsigned int indent_step,
6137 const unsigned int current_indent = 0)
6138 {
6139 switch (val.m_type)
6140 {
6141 case value_t::object:
6142 {
6143 if (val.m_value.object->empty())
6144 {
6145 o->write_characters("{}", 2);
6146 return;
6147 }
6148
6149 if (pretty_print)
6150 {
6151 o->write_characters("{\n", 2);
6152
6153 // variable to hold indentation for recursive calls
6154 const auto new_indent = current_indent + indent_step;
6155 if (JSON_UNLIKELY(indent_string.size() < new_indent))
6156 {
6157 indent_string.resize(indent_string.size() * 2, ' ');
6158 }
6159
6160 // first n-1 elements
6161 auto i = val.m_value.object->cbegin();
6162 for (std::size_t cnt = 0; cnt < val.m_value.object->size() - 1; ++cnt, ++i)
6163 {
6164 o->write_characters(indent_string.c_str(), new_indent);
6165 o->write_character('\"');
6166 dump_escaped(i->first, ensure_ascii);
6167 o->write_characters("\": ", 3);
6168 dump(i->second, true, ensure_ascii, indent_step, new_indent);
6169 o->write_characters(",\n", 2);
6170 }
6171
6172 // last element
6173 assert(i != val.m_value.object->cend());
6174 assert(std::next(i) == val.m_value.object->cend());
6175 o->write_characters(indent_string.c_str(), new_indent);
6176 o->write_character('\"');
6177 dump_escaped(i->first, ensure_ascii);
6178 o->write_characters("\": ", 3);
6179 dump(i->second, true, ensure_ascii, indent_step, new_indent);
6180
6181 o->write_character('\n');
6182 o->write_characters(indent_string.c_str(), current_indent);
6183 o->write_character('}');
6184 }
6185 else
6186 {
6187 o->write_character('{');
6188
6189 // first n-1 elements
6190 auto i = val.m_value.object->cbegin();
6191 for (std::size_t cnt = 0; cnt < val.m_value.object->size() - 1; ++cnt, ++i)
6192 {
6193 o->write_character('\"');
6194 dump_escaped(i->first, ensure_ascii);
6195 o->write_characters("\":", 2);
6196 dump(i->second, false, ensure_ascii, indent_step, current_indent);
6197 o->write_character(',');
6198 }
6199
6200 // last element
6201 assert(i != val.m_value.object->cend());
6202 assert(std::next(i) == val.m_value.object->cend());
6203 o->write_character('\"');
6204 dump_escaped(i->first, ensure_ascii);
6205 o->write_characters("\":", 2);
6206 dump(i->second, false, ensure_ascii, indent_step, current_indent);
6207
6208 o->write_character('}');
6209 }
6210
6211 return;
6212 }
6213
6214 case value_t::array:
6215 {
6216 if (val.m_value.array->empty())
6217 {
6218 o->write_characters("[]", 2);
6219 return;
6220 }
6221
6222 if (pretty_print)
6223 {
6224 o->write_characters("[\n", 2);
6225
6226 // variable to hold indentation for recursive calls
6227 const auto new_indent = current_indent + indent_step;
6228 if (JSON_UNLIKELY(indent_string.size() < new_indent))
6229 {
6230 indent_string.resize(indent_string.size() * 2, ' ');
6231 }
6232
6233 // first n-1 elements
6234 for (auto i = val.m_value.array->cbegin();
6235 i != val.m_value.array->cend() - 1; ++i)
6236 {
6237 o->write_characters(indent_string.c_str(), new_indent);
6238 dump(*i, true, ensure_ascii, indent_step, new_indent);
6239 o->write_characters(",\n", 2);
6240 }
6241
6242 // last element
6243 assert(not val.m_value.array->empty());
6244 o->write_characters(indent_string.c_str(), new_indent);
6245 dump(val.m_value.array->back(), true, ensure_ascii, indent_step, new_indent);
6246
6247 o->write_character('\n');
6248 o->write_characters(indent_string.c_str(), current_indent);
6249 o->write_character(']');
6250 }
6251 else
6252 {
6253 o->write_character('[');
6254
6255 // first n-1 elements
6256 for (auto i = val.m_value.array->cbegin();
6257 i != val.m_value.array->cend() - 1; ++i)
6258 {
6259 dump(*i, false, ensure_ascii, indent_step, current_indent);
6260 o->write_character(',');
6261 }
6262
6263 // last element
6264 assert(not val.m_value.array->empty());
6265 dump(val.m_value.array->back(), false, ensure_ascii, indent_step, current_indent);
6266
6267 o->write_character(']');
6268 }
6269
6270 return;
6271 }
6272
6273 case value_t::string:
6274 {
6275 o->write_character('\"');
6276 dump_escaped(*val.m_value.string, ensure_ascii);
6277 o->write_character('\"');
6278 return;
6279 }
6280
6281 case value_t::boolean:
6282 {
6283 if (val.m_value.boolean)
6284 {
6285 o->write_characters("true", 4);
6286 }
6287 else
6288 {
6289 o->write_characters("false", 5);
6290 }
6291 return;
6292 }
6293
6294 case value_t::number_integer:
6295 {
6296 dump_integer(val.m_value.number_integer);
6297 return;
6298 }
6299
6300 case value_t::number_unsigned:
6301 {
6302 dump_integer(val.m_value.number_unsigned);
6303 return;
6304 }
6305
6306 case value_t::number_float:
6307 {
6308 dump_float(val.m_value.number_float);
6309 return;
6310 }
6311
6312 case value_t::discarded:
6313 {
6314 o->write_characters("<discarded>", 11);
6315 return;
6316 }
6317
6318 case value_t::null:
6319 {
6320 o->write_characters("null", 4);
6321 return;
6322 }
6323 }
6324 }
6325
6326 private:
6327 /*!
6328 @brief returns the number of expected bytes following in UTF-8 string
6329
6330 @param[in] u the first byte of a UTF-8 string
6331 @return the number of expected bytes following
6332 */
6333 static constexpr std::size_t bytes_following(const uint8_t u)
6334 {
6335 return ((u <= 127) ? 0
6336 : ((192 <= u and u <= 223) ? 1
6337 : ((224 <= u and u <= 239) ? 2
6338 : ((240 <= u and u <= 247) ? 3 : std::string::npos))));
6339 }
6340
6341 /*!
6342 @brief calculates the extra space to escape a JSON string
6343
6344 @param[in] s the string to escape
6345 @param[in] ensure_ascii whether to escape non-ASCII characters with
6346 \uXXXX sequences
6347 @return the number of characters required to escape string @a s
6348
6349 @complexity Linear in the length of string @a s.
6350 */
6351 static std::size_t extra_space(const string_t& s,
6352 const bool ensure_ascii) noexcept
6353 {
6354 std::size_t res = 0;
6355
6356 for (std::size_t i = 0; i < s.size(); ++i)
6357 {
6358 switch (s[i])
6359 {
6360 // control characters that can be escaped with a backslash
6361 case '"':
6362 case '\\':
6363 case '\b':
6364 case '\f':
6365 case '\n':
6366 case '\r':
6367 case '\t':
6368 {
6369 // from c (1 byte) to \x (2 bytes)
6370 res += 1;
6371 break;
6372 }
6373
6374 // control characters that need \uxxxx escaping
6375 case 0x00:
6376 case 0x01:
6377 case 0x02:
6378 case 0x03:
6379 case 0x04:
6380 case 0x05:
6381 case 0x06:
6382 case 0x07:
6383 case 0x0b:
6384 case 0x0e:
6385 case 0x0f:
6386 case 0x10:
6387 case 0x11:
6388 case 0x12:
6389 case 0x13:
6390 case 0x14:
6391 case 0x15:
6392 case 0x16:
6393 case 0x17:
6394 case 0x18:
6395 case 0x19:
6396 case 0x1a:
6397 case 0x1b:
6398 case 0x1c:
6399 case 0x1d:
6400 case 0x1e:
6401 case 0x1f:
6402 {
6403 // from c (1 byte) to \uxxxx (6 bytes)
6404 res += 5;
6405 break;
6406 }
6407
6408 default:
6409 {
6410 if (ensure_ascii and (s[i] & 0x80 or s[i] == 0x7F))
6411 {
6412 const auto bytes = bytes_following(static_cast<uint8_t>(s[i]));
6413 if (bytes == std::string::npos)
6414 {
6415 // invalid characters are treated as is, so no
6416 // additional space will be used
6417 break;
6418 }
6419
6420 if (bytes == 3)
6421 {
6422 // codepoints that need 4 bytes (i.e., 3 additional
6423 // bytes) in UTF-8 need a surrogate pair when \u
6424 // escaping is used: from 4 bytes to \uxxxx\uxxxx
6425 // (12 bytes)
6426 res += (12 - bytes - 1);
6427 }
6428 else
6429 {
6430 // from x bytes to \uxxxx (6 bytes)
6431 res += (6 - bytes - 1);
6432 }
6433
6434 // skip the additional bytes
6435 i += bytes;
6436 }
6437 break;
6438 }
6439 }
6440 }
6441
6442 return res;
6443 }
6444
6445 static void escape_codepoint(int codepoint, string_t& result, std::size_t& pos)
6446 {
6447 // expecting a proper codepoint
6448 assert(0x00 <= codepoint and codepoint <= 0x10FFFF);
6449
6450 // the last written character was the backslash before the 'u'
6451 assert(result[pos] == '\\');
6452
6453 // write the 'u'
6454 result[++pos] = 'u';
6455
6456 // convert a number 0..15 to its hex representation (0..f)
6457 static const std::array<char, 16> hexify =
6458 {
6459 {
6460 '0', '1', '2', '3', '4', '5', '6', '7',
6461 '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'
6462 }
6463 };
6464
6465 if (codepoint < 0x10000)
6466 {
6467 // codepoints U+0000..U+FFFF can be represented as \uxxxx.
6468 result[++pos] = hexify[(codepoint >> 12) & 0x0F];
6469 result[++pos] = hexify[(codepoint >> 8) & 0x0F];
6470 result[++pos] = hexify[(codepoint >> 4) & 0x0F];
6471 result[++pos] = hexify[codepoint & 0x0F];
6472 }
6473 else
6474 {
6475 // codepoints U+10000..U+10FFFF need a surrogate pair to be
6476 // represented as \uxxxx\uxxxx.
6477 // http://www.unicode.org/faq/utf_bom.html#utf16-4
6478 codepoint -= 0x10000;
6479 const int high_surrogate = 0xD800 | ((codepoint >> 10) & 0x3FF);
6480 const int low_surrogate = 0xDC00 | (codepoint & 0x3FF);
6481 result[++pos] = hexify[(high_surrogate >> 12) & 0x0F];
6482 result[++pos] = hexify[(high_surrogate >> 8) & 0x0F];
6483 result[++pos] = hexify[(high_surrogate >> 4) & 0x0F];
6484 result[++pos] = hexify[high_surrogate & 0x0F];
6485 ++pos; // backslash is already in output
6486 result[++pos] = 'u';
6487 result[++pos] = hexify[(low_surrogate >> 12) & 0x0F];
6488 result[++pos] = hexify[(low_surrogate >> 8) & 0x0F];
6489 result[++pos] = hexify[(low_surrogate >> 4) & 0x0F];
6490 result[++pos] = hexify[low_surrogate & 0x0F];
6491 }
6492
6493 ++pos;
6494 }
6495
6496 /*!
6497 @brief dump escaped string
6498
6499 Escape a string by replacing certain special characters by a sequence of an
6500 escape character (backslash) and another character and other control
6501 characters by a sequence of "\u" followed by a four-digit hex
6502 representation. The escaped string is written to output stream @a o.
6503
6504 @param[in] s the string to escape
6505 @param[in] ensure_ascii whether to escape non-ASCII characters with
6506 \uXXXX sequences
6507
6508 @complexity Linear in the length of string @a s.
6509 */
6510 void dump_escaped(const string_t& s, const bool ensure_ascii) const
6511 {
6512 const auto space = extra_space(s, ensure_ascii);
6513 if (space == 0)
6514 {
6515 o->write_characters(s.c_str(), s.size());
6516 return;
6517 }
6518
6519 // create a result string of necessary size
6520 string_t result(s.size() + space, '\\');
6521 std::size_t pos = 0;
6522
6523 for (std::size_t i = 0; i < s.size(); ++i)
6524 {
6525 switch (s[i])
6526 {
6527 case '"': // quotation mark (0x22)
6528 {
6529 result[pos + 1] = '"';
6530 pos += 2;
6531 break;
6532 }
6533
6534 case '\\': // reverse solidus (0x5c)
6535 {
6536 // nothing to change
6537 pos += 2;
6538 break;
6539 }
6540
6541 case '\b': // backspace (0x08)
6542 {
6543 result[pos + 1] = 'b';
6544 pos += 2;
6545 break;
6546 }
6547
6548 case '\f': // formfeed (0x0c)
6549 {
6550 result[pos + 1] = 'f';
6551 pos += 2;
6552 break;
6553 }
6554
6555 case '\n': // newline (0x0a)
6556 {
6557 result[pos + 1] = 'n';
6558 pos += 2;
6559 break;
6560 }
6561
6562 case '\r': // carriage return (0x0d)
6563 {
6564 result[pos + 1] = 'r';
6565 pos += 2;
6566 break;
6567 }
6568
6569 case '\t': // horizontal tab (0x09)
6570 {
6571 result[pos + 1] = 't';
6572 pos += 2;
6573 break;
6574 }
6575
6576 default:
6577 {
6578 // escape control characters (0x00..0x1F) or, if
6579 // ensure_ascii parameter is used, non-ASCII characters
6580 if ((0x00 <= s[i] and s[i] <= 0x1F) or
6581 (ensure_ascii and (s[i] & 0x80 or s[i] == 0x7F)))
6582 {
6583 const auto bytes = bytes_following(static_cast<uint8_t>(s[i]));
6584 if (bytes == std::string::npos)
6585 {
6586 // copy invalid character as is
6587 result[pos++] = s[i];
6588 break;
6589 }
6590
6591 // check that the additional bytes are present
6592 assert(i + bytes < s.size());
6593
6594 // to use \uxxxx escaping, we first need to caluclate
6595 // the codepoint from the UTF-8 bytes
6596 int codepoint = 0;
6597
6598 assert(0 <= bytes and bytes <= 3);
6599 switch (bytes)
6600 {
6601 case 0:
6602 {
6603 codepoint = s[i] & 0xFF;
6604 break;
6605 }
6606
6607 case 1:
6608 {
6609 codepoint = ((s[i] & 0x3F) << 6)
6610 + (s[i + 1] & 0x7F);
6611 break;
6612 }
6613
6614 case 2:
6615 {
6616 codepoint = ((s[i] & 0x1F) << 12)
6617 + ((s[i + 1] & 0x7F) << 6)
6618 + (s[i + 2] & 0x7F);
6619 break;
6620 }
6621
6622 case 3:
6623 {
6624 codepoint = ((s[i] & 0xF) << 18)
6625 + ((s[i + 1] & 0x7F) << 12)
6626 + ((s[i + 2] & 0x7F) << 6)
6627 + (s[i + 3] & 0x7F);
6628 break;
6629 }
6630
6631 default:
6632 break; // LCOV_EXCL_LINE
6633 }
6634
6635 escape_codepoint(codepoint, result, pos);
6636 i += bytes;
6637 }
6638 else
6639 {
6640 // all other characters are added as-is
6641 result[pos++] = s[i];
6642 }
6643 break;
6644 }
6645 }
6646 }
6647
6648 assert(pos == result.size());
6649 o->write_characters(result.c_str(), result.size());
6650 }
6651
6652 /*!
6653 @brief dump an integer
6654
6655 Dump a given integer to output stream @a o. Works internally with
6656 @a number_buffer.
6657
6658 @param[in] x integer number (signed or unsigned) to dump
6659 @tparam NumberType either @a number_integer_t or @a number_unsigned_t
6660 */
6661 template <
6662 typename NumberType,
6663 detail::enable_if_t<std::is_same<NumberType, number_unsigned_t>::value or
6664 std::is_same<NumberType, number_integer_t>::value,
6665 int> = 0 >
6666 void dump_integer(NumberType x)
6667 {
6668 // special case for "0"
6669 if (x == 0)
6670 {
6671 o->write_character('0');
6672 return;
6673 }
6674
6675 const bool is_negative = (x <= 0) and (x != 0); // see issue #755
6676 std::size_t i = 0;
6677
6678 while (x != 0)
6679 {
6680 // spare 1 byte for '\0'
6681 assert(i < number_buffer.size() - 1);
6682
6683 const auto digit = std::labs(static_cast<long>(x % 10));
6684 number_buffer[i++] = static_cast<char>('0' + digit);
6685 x /= 10;
6686 }
6687
6688 if (is_negative)
6689 {
6690 // make sure there is capacity for the '-'
6691 assert(i < number_buffer.size() - 2);
6692 number_buffer[i++] = '-';
6693 }
6694
6695 std::reverse(number_buffer.begin(), number_buffer.begin() + i);
6696 o->write_characters(number_buffer.data(), i);
6697 }
6698
6699 /*!
6700 @brief dump a floating-point number
6701
6702 Dump a given floating-point number to output stream @a o. Works internally
6703 with @a number_buffer.
6704
6705 @param[in] x floating-point number to dump
6706 */
6707 void dump_float(number_float_t x)
6708 {
6709 // NaN / inf
6710 if (not std::isfinite(x) or std::isnan(x))
6711 {
6712 o->write_characters("null", 4);
6713 return;
6714 }
6715
6716 // get number of digits for a text -> float -> text round-trip
6717 static constexpr auto d = std::numeric_limits<number_float_t>::digits10;
6718
6719 // the actual conversion
6720 std::ptrdiff_t len = snprintf(number_buffer.data(), number_buffer.size(), "%.*g", d, x);
6721
6722 // negative value indicates an error
6723 assert(len > 0);
6724 // check if buffer was large enough
6725 assert(static_cast<std::size_t>(len) < number_buffer.size());
6726
6727 // erase thousands separator
6728 if (thousands_sep != '\0')
6729 {
6730 const auto end = std::remove(number_buffer.begin(),
6731 number_buffer.begin() + len, thousands_sep);
6732 std::fill(end, number_buffer.end(), '\0');
6733 assert((end - number_buffer.begin()) <= len);
6734 len = (end - number_buffer.begin());
6735 }
6736
6737 // convert decimal point to '.'
6738 if (decimal_point != '\0' and decimal_point != '.')
6739 {
6740 const auto dec_pos = std::find(number_buffer.begin(), number_buffer.end(), decimal_point);
6741 if (dec_pos != number_buffer.end())
6742 {
6743 *dec_pos = '.';
6744 }
6745 }
6746
6747 o->write_characters(number_buffer.data(), static_cast<std::size_t>(len));
6748
6749 // determine if need to append ".0"
6750 const bool value_is_int_like =
6751 std::none_of(number_buffer.begin(), number_buffer.begin() + len + 1,
6752 [](char c)
6753 {
6754 return (c == '.' or c == 'e');
6755 });
6756
6757 if (value_is_int_like)
6758 {
6759 o->write_characters(".0", 2);
6760 }
6761 }
6762
6763 private:
6764 /// the output of the serializer
6765 output_adapter_t<char> o = nullptr;
6766
6767 /// a (hopefully) large enough character buffer
6768 std::array<char, 64> number_buffer{{}};
6769
6770 /// the locale
6771 const std::lconv* loc = nullptr;
6772 /// the locale's thousand separator character
6773 const char thousands_sep = '\0';
6774 /// the locale's decimal point character
6775 const char decimal_point = '\0';
6776
6777 /// the indentation character
6778 const char indent_char;
6779
6780 /// the indentation string
6781 string_t indent_string;
6782};
6783
6784template<typename BasicJsonType>
6785class json_ref
6786{
6787 public:
6788 using value_type = BasicJsonType;
6789
6790 json_ref(value_type&& value)
6791 : owned_value(std::move(value)),
6792 value_ref(&owned_value),
6793 is_rvalue(true)
6794 {}
6795
6796 json_ref(const value_type& value)
6797 : value_ref(const_cast<value_type*>(&value)),
6798 is_rvalue(false)
6799 {}
6800
6801 json_ref(std::initializer_list<json_ref> init)
6802 : owned_value(init),
6803 value_ref(&owned_value),
6804 is_rvalue(true)
6805 {}
6806
6807 template <class... Args>
6808 json_ref(Args... args)
6809 : owned_value(std::forward<Args>(args)...),
6810 value_ref(&owned_value),
6811 is_rvalue(true)
6812 {}
6813
6814 // class should be movable only
6815 json_ref(json_ref&&) = default;
6816 json_ref(const json_ref&) = delete;
6817 json_ref& operator=(const json_ref&) = delete;
6818
6819 value_type moved_or_copied() const
6820 {
6821 if (is_rvalue)
6822 {
6823 return std::move(*value_ref);
6824 }
6825 return *value_ref;
6826 }
6827
6828 value_type const& operator*() const
6829 {
6830 return *static_cast<value_type const*>(value_ref);
6831 }
6832
6833 value_type const* operator->() const
6834 {
6835 return static_cast<value_type const*>(value_ref);
6836 }
6837
6838 private:
6839 mutable value_type owned_value = nullptr;
6840 value_type* value_ref = nullptr;
6841 const bool is_rvalue;
6842};
6843
6844} // namespace detail
Ed Tanous3dac7492017-08-02 13:46:20 -07006845
6846/// namespace to hold default `to_json` / `from_json` functions
6847namespace
6848{
6849constexpr const auto& to_json = detail::static_const<detail::to_json_fn>::value;
6850constexpr const auto& from_json = detail::static_const<detail::from_json_fn>::value;
6851}
6852
6853
6854/*!
6855@brief default JSONSerializer template argument
6856
6857This serializer ignores the template arguments and uses ADL
6858([argument-dependent lookup](http://en.cppreference.com/w/cpp/language/adl))
6859for serialization.
6860*/
Ed Tanousba9f9a62017-10-11 16:40:35 -07006861template<typename, typename>
Ed Tanous3dac7492017-08-02 13:46:20 -07006862struct adl_serializer
6863{
6864 /*!
6865 @brief convert a JSON value to any value type
6866
6867 This function is usually called by the `get()` function of the
6868 @ref basic_json class (either explicit or via conversion operators).
6869
6870 @param[in] j JSON value to read from
6871 @param[in,out] val value to write to
6872 */
6873 template<typename BasicJsonType, typename ValueType>
6874 static void from_json(BasicJsonType&& j, ValueType& val) noexcept(
6875 noexcept(::nlohmann::from_json(std::forward<BasicJsonType>(j), val)))
6876 {
6877 ::nlohmann::from_json(std::forward<BasicJsonType>(j), val);
6878 }
6879
6880 /*!
6881 @brief convert any value type to a JSON value
6882
6883 This function is usually called by the constructors of the @ref basic_json
6884 class.
6885
6886 @param[in,out] j JSON value to write to
6887 @param[in] val value to read from
6888 */
6889 template<typename BasicJsonType, typename ValueType>
6890 static void to_json(BasicJsonType& j, ValueType&& val) noexcept(
6891 noexcept(::nlohmann::to_json(j, std::forward<ValueType>(val))))
6892 {
6893 ::nlohmann::to_json(j, std::forward<ValueType>(val));
6894 }
6895};
6896
Ed Tanousba9f9a62017-10-11 16:40:35 -07006897/*!
6898@brief JSON Pointer
6899
6900A JSON pointer defines a string syntax for identifying a specific value
6901within a JSON document. It can be used with functions `at` and
6902`operator[]`. Furthermore, JSON pointers are the base for JSON patches.
6903
6904@sa [RFC 6901](https://tools.ietf.org/html/rfc6901)
6905
6906@since version 2.0.0
6907*/
6908class json_pointer
6909{
6910 /// allow basic_json to access private members
6911 NLOHMANN_BASIC_JSON_TPL_DECLARATION
6912 friend class basic_json;
6913
6914 public:
6915 /*!
6916 @brief create JSON pointer
6917
6918 Create a JSON pointer according to the syntax described in
6919 [Section 3 of RFC6901](https://tools.ietf.org/html/rfc6901#section-3).
6920
6921 @param[in] s string representing the JSON pointer; if omitted, the empty
6922 string is assumed which references the whole JSON value
6923
6924 @throw parse_error.107 if the given JSON pointer @a s is nonempty and
6925 does not begin with a slash (`/`); see example below
6926
6927 @throw parse_error.108 if a tilde (`~`) in the given JSON pointer @a s
6928 is not followed by `0` (representing `~`) or `1` (representing `/`);
6929 see example below
6930
6931 @liveexample{The example shows the construction several valid JSON
6932 pointers as well as the exceptional behavior.,json_pointer}
6933
6934 @since version 2.0.0
6935 */
6936 explicit json_pointer(const std::string& s = "") : reference_tokens(split(s)) {}
6937
6938 /*!
6939 @brief return a string representation of the JSON pointer
6940
6941 @invariant For each JSON pointer `ptr`, it holds:
6942 @code {.cpp}
6943 ptr == json_pointer(ptr.to_string());
6944 @endcode
6945
6946 @return a string representation of the JSON pointer
6947
6948 @liveexample{The example shows the result of `to_string`.,
6949 json_pointer__to_string}
6950
6951 @since version 2.0.0
6952 */
6953 std::string to_string() const noexcept
6954 {
6955 return std::accumulate(reference_tokens.begin(), reference_tokens.end(),
6956 std::string{},
6957 [](const std::string & a, const std::string & b)
6958 {
6959 return a + "/" + escape(b);
6960 });
6961 }
6962
6963 /// @copydoc to_string()
6964 operator std::string() const
6965 {
6966 return to_string();
6967 }
6968
6969 private:
6970 /*!
6971 @brief remove and return last reference pointer
6972 @throw out_of_range.405 if JSON pointer has no parent
6973 */
6974 std::string pop_back()
6975 {
6976 if (JSON_UNLIKELY(is_root()))
6977 {
6978 JSON_THROW(detail::out_of_range::create(405, "JSON pointer has no parent"));
6979 }
6980
6981 auto last = reference_tokens.back();
6982 reference_tokens.pop_back();
6983 return last;
6984 }
6985
6986 /// return whether pointer points to the root document
6987 bool is_root() const
6988 {
6989 return reference_tokens.empty();
6990 }
6991
6992 json_pointer top() const
6993 {
6994 if (JSON_UNLIKELY(is_root()))
6995 {
6996 JSON_THROW(detail::out_of_range::create(405, "JSON pointer has no parent"));
6997 }
6998
6999 json_pointer result = *this;
7000 result.reference_tokens = {reference_tokens[0]};
7001 return result;
7002 }
7003
7004
7005 /*!
7006 @brief create and return a reference to the pointed to value
7007
7008 @complexity Linear in the number of reference tokens.
7009
7010 @throw parse_error.109 if array index is not a number
7011 @throw type_error.313 if value cannot be unflattened
7012 */
7013 NLOHMANN_BASIC_JSON_TPL_DECLARATION
7014 NLOHMANN_BASIC_JSON_TPL& get_and_create(NLOHMANN_BASIC_JSON_TPL& j) const;
7015
7016 /*!
7017 @brief return a reference to the pointed to value
7018
7019 @note This version does not throw if a value is not present, but tries to
7020 create nested values instead. For instance, calling this function
7021 with pointer `"/this/that"` on a null value is equivalent to calling
7022 `operator[]("this").operator[]("that")` on that value, effectively
7023 changing the null value to an object.
7024
7025 @param[in] ptr a JSON value
7026
7027 @return reference to the JSON value pointed to by the JSON pointer
7028
7029 @complexity Linear in the length of the JSON pointer.
7030
7031 @throw parse_error.106 if an array index begins with '0'
7032 @throw parse_error.109 if an array index was not a number
7033 @throw out_of_range.404 if the JSON pointer can not be resolved
7034 */
7035 NLOHMANN_BASIC_JSON_TPL_DECLARATION
7036 NLOHMANN_BASIC_JSON_TPL& get_unchecked(NLOHMANN_BASIC_JSON_TPL* ptr) const;
7037
7038 /*!
7039 @throw parse_error.106 if an array index begins with '0'
7040 @throw parse_error.109 if an array index was not a number
7041 @throw out_of_range.402 if the array index '-' is used
7042 @throw out_of_range.404 if the JSON pointer can not be resolved
7043 */
7044 NLOHMANN_BASIC_JSON_TPL_DECLARATION
7045 NLOHMANN_BASIC_JSON_TPL& get_checked(NLOHMANN_BASIC_JSON_TPL* ptr) const;
7046
7047 /*!
7048 @brief return a const reference to the pointed to value
7049
7050 @param[in] ptr a JSON value
7051
7052 @return const reference to the JSON value pointed to by the JSON
7053 pointer
7054
7055 @throw parse_error.106 if an array index begins with '0'
7056 @throw parse_error.109 if an array index was not a number
7057 @throw out_of_range.402 if the array index '-' is used
7058 @throw out_of_range.404 if the JSON pointer can not be resolved
7059 */
7060 NLOHMANN_BASIC_JSON_TPL_DECLARATION
7061 const NLOHMANN_BASIC_JSON_TPL& get_unchecked(const NLOHMANN_BASIC_JSON_TPL* ptr) const;
7062
7063 /*!
7064 @throw parse_error.106 if an array index begins with '0'
7065 @throw parse_error.109 if an array index was not a number
7066 @throw out_of_range.402 if the array index '-' is used
7067 @throw out_of_range.404 if the JSON pointer can not be resolved
7068 */
7069 NLOHMANN_BASIC_JSON_TPL_DECLARATION
7070 const NLOHMANN_BASIC_JSON_TPL& get_checked(const NLOHMANN_BASIC_JSON_TPL* ptr) const;
7071
7072 /*!
7073 @brief split the string input to reference tokens
7074
7075 @note This function is only called by the json_pointer constructor.
7076 All exceptions below are documented there.
7077
7078 @throw parse_error.107 if the pointer is not empty or begins with '/'
7079 @throw parse_error.108 if character '~' is not followed by '0' or '1'
7080 */
7081 static std::vector<std::string> split(const std::string& reference_string)
7082 {
7083 std::vector<std::string> result;
7084
7085 // special case: empty reference string -> no reference tokens
7086 if (reference_string.empty())
7087 {
7088 return result;
7089 }
7090
7091 // check if nonempty reference string begins with slash
7092 if (JSON_UNLIKELY(reference_string[0] != '/'))
7093 {
7094 JSON_THROW(detail::parse_error::create(107, 1,
7095 "JSON pointer must be empty or begin with '/' - was: '" +
7096 reference_string + "'"));
7097 }
7098
7099 // extract the reference tokens:
7100 // - slash: position of the last read slash (or end of string)
7101 // - start: position after the previous slash
7102 for (
7103 // search for the first slash after the first character
7104 std::size_t slash = reference_string.find_first_of('/', 1),
7105 // set the beginning of the first reference token
7106 start = 1;
7107 // we can stop if start == string::npos+1 = 0
7108 start != 0;
7109 // set the beginning of the next reference token
7110 // (will eventually be 0 if slash == std::string::npos)
7111 start = slash + 1,
7112 // find next slash
7113 slash = reference_string.find_first_of('/', start))
7114 {
7115 // use the text between the beginning of the reference token
7116 // (start) and the last slash (slash).
7117 auto reference_token = reference_string.substr(start, slash - start);
7118
7119 // check reference tokens are properly escaped
7120 for (std::size_t pos = reference_token.find_first_of('~');
7121 pos != std::string::npos;
7122 pos = reference_token.find_first_of('~', pos + 1))
7123 {
7124 assert(reference_token[pos] == '~');
7125
7126 // ~ must be followed by 0 or 1
7127 if (JSON_UNLIKELY(pos == reference_token.size() - 1 or
7128 (reference_token[pos + 1] != '0' and
7129 reference_token[pos + 1] != '1')))
7130 {
7131 JSON_THROW(detail::parse_error::create(108, 0, "escape character '~' must be followed with '0' or '1'"));
7132 }
7133 }
7134
7135 // finally, store the reference token
7136 unescape(reference_token);
7137 result.push_back(reference_token);
7138 }
7139
7140 return result;
7141 }
7142
7143 /*!
7144 @brief replace all occurrences of a substring by another string
7145
7146 @param[in,out] s the string to manipulate; changed so that all
7147 occurrences of @a f are replaced with @a t
7148 @param[in] f the substring to replace with @a t
7149 @param[in] t the string to replace @a f
7150
7151 @pre The search string @a f must not be empty. **This precondition is
7152 enforced with an assertion.**
7153
7154 @since version 2.0.0
7155 */
7156 static void replace_substring(std::string& s, const std::string& f,
7157 const std::string& t)
7158 {
7159 assert(not f.empty());
7160 for (auto pos = s.find(f); // find first occurrence of f
7161 pos != std::string::npos; // make sure f was found
7162 s.replace(pos, f.size(), t), // replace with t, and
7163 pos = s.find(f, pos + t.size())) // find next occurrence of f
7164 {}
7165 }
7166
7167 /// escape "~"" to "~0" and "/" to "~1"
7168 static std::string escape(std::string s)
7169 {
7170 replace_substring(s, "~", "~0");
7171 replace_substring(s, "/", "~1");
7172 return s;
7173 }
7174
7175 /// unescape "~1" to tilde and "~0" to slash (order is important!)
7176 static void unescape(std::string& s)
7177 {
7178 replace_substring(s, "~1", "/");
7179 replace_substring(s, "~0", "~");
7180 }
7181
7182 /*!
7183 @param[in] reference_string the reference string to the current value
7184 @param[in] value the value to consider
7185 @param[in,out] result the result object to insert values to
7186
7187 @note Empty objects or arrays are flattened to `null`.
7188 */
7189 NLOHMANN_BASIC_JSON_TPL_DECLARATION
7190 static void flatten(const std::string& reference_string,
7191 const NLOHMANN_BASIC_JSON_TPL& value,
7192 NLOHMANN_BASIC_JSON_TPL& result);
7193
7194 /*!
7195 @param[in] value flattened JSON
7196
7197 @return unflattened JSON
7198
7199 @throw parse_error.109 if array index is not a number
7200 @throw type_error.314 if value is not an object
7201 @throw type_error.315 if object values are not primitive
7202 @throw type_error.313 if value cannot be unflattened
7203 */
7204 NLOHMANN_BASIC_JSON_TPL_DECLARATION
7205 static NLOHMANN_BASIC_JSON_TPL
7206 unflatten(const NLOHMANN_BASIC_JSON_TPL& value);
7207
7208 friend bool operator==(json_pointer const& lhs,
7209 json_pointer const& rhs) noexcept;
7210
7211 friend bool operator!=(json_pointer const& lhs,
7212 json_pointer const& rhs) noexcept;
7213
7214 /// the reference tokens
7215 std::vector<std::string> reference_tokens;
7216};
Ed Tanous3dac7492017-08-02 13:46:20 -07007217
7218/*!
7219@brief a class to store JSON values
7220
7221@tparam ObjectType type for JSON objects (`std::map` by default; will be used
7222in @ref object_t)
7223@tparam ArrayType type for JSON arrays (`std::vector` by default; will be used
7224in @ref array_t)
7225@tparam StringType type for JSON strings and object keys (`std::string` by
7226default; will be used in @ref string_t)
7227@tparam BooleanType type for JSON booleans (`bool` by default; will be used
7228in @ref boolean_t)
7229@tparam NumberIntegerType type for JSON integer numbers (`int64_t` by
7230default; will be used in @ref number_integer_t)
7231@tparam NumberUnsignedType type for JSON unsigned integer numbers (@c
7232`uint64_t` by default; will be used in @ref number_unsigned_t)
7233@tparam NumberFloatType type for JSON floating-point numbers (`double` by
7234default; will be used in @ref number_float_t)
7235@tparam AllocatorType type of the allocator to use (`std::allocator` by
7236default)
7237@tparam JSONSerializer the serializer to resolve internal calls to `to_json()`
7238and `from_json()` (@ref adl_serializer by default)
7239
7240@requirement The class satisfies the following concept requirements:
7241- Basic
7242 - [DefaultConstructible](http://en.cppreference.com/w/cpp/concept/DefaultConstructible):
7243 JSON values can be default constructed. The result will be a JSON null
7244 value.
7245 - [MoveConstructible](http://en.cppreference.com/w/cpp/concept/MoveConstructible):
7246 A JSON value can be constructed from an rvalue argument.
7247 - [CopyConstructible](http://en.cppreference.com/w/cpp/concept/CopyConstructible):
7248 A JSON value can be copy-constructed from an lvalue expression.
7249 - [MoveAssignable](http://en.cppreference.com/w/cpp/concept/MoveAssignable):
7250 A JSON value van be assigned from an rvalue argument.
7251 - [CopyAssignable](http://en.cppreference.com/w/cpp/concept/CopyAssignable):
7252 A JSON value can be copy-assigned from an lvalue expression.
7253 - [Destructible](http://en.cppreference.com/w/cpp/concept/Destructible):
7254 JSON values can be destructed.
7255- Layout
7256 - [StandardLayoutType](http://en.cppreference.com/w/cpp/concept/StandardLayoutType):
7257 JSON values have
7258 [standard layout](http://en.cppreference.com/w/cpp/language/data_members#Standard_layout):
7259 All non-static data members are private and standard layout types, the
7260 class has no virtual functions or (virtual) base classes.
7261- Library-wide
7262 - [EqualityComparable](http://en.cppreference.com/w/cpp/concept/EqualityComparable):
7263 JSON values can be compared with `==`, see @ref
7264 operator==(const_reference,const_reference).
7265 - [LessThanComparable](http://en.cppreference.com/w/cpp/concept/LessThanComparable):
7266 JSON values can be compared with `<`, see @ref
7267 operator<(const_reference,const_reference).
7268 - [Swappable](http://en.cppreference.com/w/cpp/concept/Swappable):
7269 Any JSON lvalue or rvalue of can be swapped with any lvalue or rvalue of
7270 other compatible types, using unqualified function call @ref swap().
7271 - [NullablePointer](http://en.cppreference.com/w/cpp/concept/NullablePointer):
7272 JSON values can be compared against `std::nullptr_t` objects which are used
7273 to model the `null` value.
7274- Container
7275 - [Container](http://en.cppreference.com/w/cpp/concept/Container):
7276 JSON values can be used like STL containers and provide iterator access.
7277 - [ReversibleContainer](http://en.cppreference.com/w/cpp/concept/ReversibleContainer);
7278 JSON values can be used like STL containers and provide reverse iterator
7279 access.
7280
7281@invariant The member variables @a m_value and @a m_type have the following
7282relationship:
7283- If `m_type == value_t::object`, then `m_value.object != nullptr`.
7284- If `m_type == value_t::array`, then `m_value.array != nullptr`.
7285- If `m_type == value_t::string`, then `m_value.string != nullptr`.
7286The invariants are checked by member function assert_invariant().
7287
7288@internal
7289@note ObjectType trick from http://stackoverflow.com/a/9860911
7290@endinternal
7291
7292@see [RFC 7159: The JavaScript Object Notation (JSON) Data Interchange
7293Format](http://rfc7159.net/rfc7159)
7294
7295@since version 1.0.0
7296
7297@nosubgrouping
7298*/
Ed Tanousba9f9a62017-10-11 16:40:35 -07007299NLOHMANN_BASIC_JSON_TPL_DECLARATION
Ed Tanous3dac7492017-08-02 13:46:20 -07007300class basic_json
7301{
7302 private:
7303 template<detail::value_t> friend struct detail::external_constructor;
Ed Tanousba9f9a62017-10-11 16:40:35 -07007304 friend ::nlohmann::json_pointer;
7305 friend ::nlohmann::detail::parser<basic_json>;
7306 friend ::nlohmann::detail::serializer<basic_json>;
7307 template<typename BasicJsonType>
7308 friend class ::nlohmann::detail::iter_impl;
7309 template<typename BasicJsonType, typename CharType>
7310 friend class ::nlohmann::detail::binary_writer;
7311 template<typename BasicJsonType>
7312 friend class ::nlohmann::detail::binary_reader;
7313
Ed Tanous3dac7492017-08-02 13:46:20 -07007314 /// workaround type for MSVC
Ed Tanousba9f9a62017-10-11 16:40:35 -07007315 using basic_json_t = NLOHMANN_BASIC_JSON_TPL;
7316
7317 // convenience aliases for types residing in namespace detail;
7318 using lexer = ::nlohmann::detail::lexer<basic_json>;
7319 using parser = ::nlohmann::detail::parser<basic_json>;
7320
7321 using primitive_iterator_t = ::nlohmann::detail::primitive_iterator_t;
7322 template<typename BasicJsonType>
7323 using internal_iterator = ::nlohmann::detail::internal_iterator<BasicJsonType>;
7324 template<typename BasicJsonType>
7325 using iter_impl = ::nlohmann::detail::iter_impl<BasicJsonType>;
7326 template<typename Iterator>
7327 using iteration_proxy = ::nlohmann::detail::iteration_proxy<Iterator>;
7328 template<typename Base> using json_reverse_iterator = ::nlohmann::detail::json_reverse_iterator<Base>;
7329
7330 template<typename CharType>
7331 using output_adapter_t = ::nlohmann::detail::output_adapter_t<CharType>;
7332
7333 using binary_reader = ::nlohmann::detail::binary_reader<basic_json>;
7334 template<typename CharType> using binary_writer = ::nlohmann::detail::binary_writer<basic_json, CharType>;
7335
7336 using serializer = ::nlohmann::detail::serializer<basic_json>;
Ed Tanous3dac7492017-08-02 13:46:20 -07007337
7338 public:
7339 using value_t = detail::value_t;
7340 // forward declarations
Ed Tanousba9f9a62017-10-11 16:40:35 -07007341 using json_pointer = ::nlohmann::json_pointer;
Ed Tanous3dac7492017-08-02 13:46:20 -07007342 template<typename T, typename SFINAE>
7343 using json_serializer = JSONSerializer<T, SFINAE>;
7344
Ed Tanousba9f9a62017-10-11 16:40:35 -07007345 using initializer_list_t = std::initializer_list<detail::json_ref<basic_json>>;
7346
7347 ////////////////
7348 // exceptions //
7349 ////////////////
7350
7351 /// @name exceptions
7352 /// Classes to implement user-defined exceptions.
7353 /// @{
7354
7355 /// @copydoc detail::exception
7356 using exception = detail::exception;
7357 /// @copydoc detail::parse_error
7358 using parse_error = detail::parse_error;
7359 /// @copydoc detail::invalid_iterator
7360 using invalid_iterator = detail::invalid_iterator;
7361 /// @copydoc detail::type_error
7362 using type_error = detail::type_error;
7363 /// @copydoc detail::out_of_range
7364 using out_of_range = detail::out_of_range;
7365 /// @copydoc detail::other_error
7366 using other_error = detail::other_error;
7367
7368 /// @}
7369
7370
Ed Tanous3dac7492017-08-02 13:46:20 -07007371 /////////////////////
7372 // container types //
7373 /////////////////////
7374
7375 /// @name container types
7376 /// The canonic container types to use @ref basic_json like any other STL
7377 /// container.
7378 /// @{
7379
7380 /// the type of elements in a basic_json container
7381 using value_type = basic_json;
7382
7383 /// the type of an element reference
7384 using reference = value_type&;
7385 /// the type of an element const reference
7386 using const_reference = const value_type&;
7387
7388 /// a type to represent differences between iterators
7389 using difference_type = std::ptrdiff_t;
7390 /// a type to represent container sizes
7391 using size_type = std::size_t;
7392
7393 /// the allocator type
7394 using allocator_type = AllocatorType<basic_json>;
7395
7396 /// the type of an element pointer
7397 using pointer = typename std::allocator_traits<allocator_type>::pointer;
7398 /// the type of an element const pointer
7399 using const_pointer = typename std::allocator_traits<allocator_type>::const_pointer;
7400
7401 /// an iterator for a basic_json container
7402 using iterator = iter_impl<basic_json>;
7403 /// a const iterator for a basic_json container
7404 using const_iterator = iter_impl<const basic_json>;
7405 /// a reverse iterator for a basic_json container
7406 using reverse_iterator = json_reverse_iterator<typename basic_json::iterator>;
7407 /// a const reverse iterator for a basic_json container
7408 using const_reverse_iterator = json_reverse_iterator<typename basic_json::const_iterator>;
7409
7410 /// @}
7411
7412
7413 /*!
7414 @brief returns the allocator associated with the container
7415 */
7416 static allocator_type get_allocator()
7417 {
7418 return allocator_type();
7419 }
7420
7421 /*!
7422 @brief returns version information on the library
7423
7424 This function returns a JSON object with information about the library,
7425 including the version number and information on the platform and compiler.
7426
7427 @return JSON object holding version information
7428 key | description
7429 ----------- | ---------------
7430 `compiler` | Information on the used compiler. It is an object with the following keys: `c++` (the used C++ standard), `family` (the compiler family; possible values are `clang`, `icc`, `gcc`, `ilecpp`, `msvc`, `pgcpp`, `sunpro`, and `unknown`), and `version` (the compiler version).
7431 `copyright` | The copyright line for the library as string.
7432 `name` | The name of the library as string.
7433 `platform` | The used platform as string. Possible values are `win32`, `linux`, `apple`, `unix`, and `unknown`.
7434 `url` | The URL of the project as string.
7435 `version` | The version of the library. It is an object with the following keys: `major`, `minor`, and `patch` as defined by [Semantic Versioning](http://semver.org), and `string` (the version string).
7436
7437 @liveexample{The following code shows an example output of the `meta()`
7438 function.,meta}
7439
Ed Tanousba9f9a62017-10-11 16:40:35 -07007440 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
7441 changes to any JSON value.
7442
Ed Tanous3dac7492017-08-02 13:46:20 -07007443 @complexity Constant.
7444
7445 @since 2.1.0
7446 */
7447 static basic_json meta()
7448 {
7449 basic_json result;
7450
7451 result["copyright"] = "(C) 2013-2017 Niels Lohmann";
7452 result["name"] = "JSON for Modern C++";
7453 result["url"] = "https://github.com/nlohmann/json";
7454 result["version"] =
7455 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07007456 {"string", "2.1.1"}, {"major", 2}, {"minor", 1}, {"patch", 1}
Ed Tanous3dac7492017-08-02 13:46:20 -07007457 };
7458
7459#ifdef _WIN32
7460 result["platform"] = "win32";
7461#elif defined __linux__
7462 result["platform"] = "linux";
7463#elif defined __APPLE__
7464 result["platform"] = "apple";
7465#elif defined __unix__
7466 result["platform"] = "unix";
7467#else
7468 result["platform"] = "unknown";
7469#endif
7470
Ed Tanousba9f9a62017-10-11 16:40:35 -07007471#if defined(__ICC) || defined(__INTEL_COMPILER)
Ed Tanous3dac7492017-08-02 13:46:20 -07007472 result["compiler"] = {{"family", "icc"}, {"version", __INTEL_COMPILER}};
Ed Tanousba9f9a62017-10-11 16:40:35 -07007473#elif defined(__clang__)
7474 result["compiler"] = {{"family", "clang"}, {"version", __clang_version__}};
Ed Tanous3dac7492017-08-02 13:46:20 -07007475#elif defined(__GNUC__) || defined(__GNUG__)
7476 result["compiler"] = {{"family", "gcc"}, {"version", std::to_string(__GNUC__) + "." + std::to_string(__GNUC_MINOR__) + "." + std::to_string(__GNUC_PATCHLEVEL__)}};
7477#elif defined(__HP_cc) || defined(__HP_aCC)
7478 result["compiler"] = "hp"
7479#elif defined(__IBMCPP__)
7480 result["compiler"] = {{"family", "ilecpp"}, {"version", __IBMCPP__}};
7481#elif defined(_MSC_VER)
7482 result["compiler"] = {{"family", "msvc"}, {"version", _MSC_VER}};
7483#elif defined(__PGI)
7484 result["compiler"] = {{"family", "pgcpp"}, {"version", __PGI}};
7485#elif defined(__SUNPRO_CC)
7486 result["compiler"] = {{"family", "sunpro"}, {"version", __SUNPRO_CC}};
7487#else
7488 result["compiler"] = {{"family", "unknown"}, {"version", "unknown"}};
7489#endif
7490
7491#ifdef __cplusplus
7492 result["compiler"]["c++"] = std::to_string(__cplusplus);
7493#else
7494 result["compiler"]["c++"] = "unknown";
7495#endif
7496 return result;
7497 }
7498
7499
7500 ///////////////////////////
7501 // JSON value data types //
7502 ///////////////////////////
7503
7504 /// @name JSON value data types
7505 /// The data types to store a JSON value. These types are derived from
7506 /// the template arguments passed to class @ref basic_json.
7507 /// @{
7508
7509 /*!
7510 @brief a type for an object
7511
7512 [RFC 7159](http://rfc7159.net/rfc7159) describes JSON objects as follows:
7513 > An object is an unordered collection of zero or more name/value pairs,
7514 > where a name is a string and a value is a string, number, boolean, null,
7515 > object, or array.
7516
7517 To store objects in C++, a type is defined by the template parameters
7518 described below.
7519
7520 @tparam ObjectType the container to store objects (e.g., `std::map` or
7521 `std::unordered_map`)
7522 @tparam StringType the type of the keys or names (e.g., `std::string`).
7523 The comparison function `std::less<StringType>` is used to order elements
7524 inside the container.
7525 @tparam AllocatorType the allocator to use for objects (e.g.,
7526 `std::allocator`)
7527
7528 #### Default type
7529
7530 With the default values for @a ObjectType (`std::map`), @a StringType
7531 (`std::string`), and @a AllocatorType (`std::allocator`), the default
7532 value for @a object_t is:
7533
7534 @code {.cpp}
7535 std::map<
7536 std::string, // key_type
7537 basic_json, // value_type
7538 std::less<std::string>, // key_compare
7539 std::allocator<std::pair<const std::string, basic_json>> // allocator_type
7540 >
7541 @endcode
7542
7543 #### Behavior
7544
7545 The choice of @a object_t influences the behavior of the JSON class. With
7546 the default type, objects have the following behavior:
7547
7548 - When all names are unique, objects will be interoperable in the sense
7549 that all software implementations receiving that object will agree on
7550 the name-value mappings.
7551 - When the names within an object are not unique, later stored name/value
7552 pairs overwrite previously stored name/value pairs, leaving the used
7553 names unique. For instance, `{"key": 1}` and `{"key": 2, "key": 1}` will
7554 be treated as equal and both stored as `{"key": 1}`.
7555 - Internally, name/value pairs are stored in lexicographical order of the
7556 names. Objects will also be serialized (see @ref dump) in this order.
7557 For instance, `{"b": 1, "a": 2}` and `{"a": 2, "b": 1}` will be stored
7558 and serialized as `{"a": 2, "b": 1}`.
7559 - When comparing objects, the order of the name/value pairs is irrelevant.
7560 This makes objects interoperable in the sense that they will not be
7561 affected by these differences. For instance, `{"b": 1, "a": 2}` and
7562 `{"a": 2, "b": 1}` will be treated as equal.
7563
7564 #### Limits
7565
7566 [RFC 7159](http://rfc7159.net/rfc7159) specifies:
7567 > An implementation may set limits on the maximum depth of nesting.
7568
Ed Tanousba9f9a62017-10-11 16:40:35 -07007569 In this class, the object's limit of nesting is not explicitly constrained.
Ed Tanous3dac7492017-08-02 13:46:20 -07007570 However, a maximum depth of nesting may be introduced by the compiler or
7571 runtime environment. A theoretical limit can be queried by calling the
7572 @ref max_size function of a JSON object.
7573
7574 #### Storage
7575
7576 Objects are stored as pointers in a @ref basic_json type. That is, for any
7577 access to object values, a pointer of type `object_t*` must be
7578 dereferenced.
7579
7580 @sa @ref array_t -- type for an array value
7581
7582 @since version 1.0.0
7583
7584 @note The order name/value pairs are added to the object is *not*
7585 preserved by the library. Therefore, iterating an object may return
7586 name/value pairs in a different order than they were originally stored. In
7587 fact, keys will be traversed in alphabetical order as `std::map` with
7588 `std::less` is used by default. Please note this behavior conforms to [RFC
7589 7159](http://rfc7159.net/rfc7159), because any order implements the
7590 specified "unordered" nature of JSON objects.
7591 */
7592 using object_t = ObjectType<StringType,
7593 basic_json,
7594 std::less<StringType>,
7595 AllocatorType<std::pair<const StringType,
7596 basic_json>>>;
7597
7598 /*!
7599 @brief a type for an array
7600
7601 [RFC 7159](http://rfc7159.net/rfc7159) describes JSON arrays as follows:
7602 > An array is an ordered sequence of zero or more values.
7603
7604 To store objects in C++, a type is defined by the template parameters
7605 explained below.
7606
7607 @tparam ArrayType container type to store arrays (e.g., `std::vector` or
7608 `std::list`)
7609 @tparam AllocatorType allocator to use for arrays (e.g., `std::allocator`)
7610
7611 #### Default type
7612
7613 With the default values for @a ArrayType (`std::vector`) and @a
7614 AllocatorType (`std::allocator`), the default value for @a array_t is:
7615
7616 @code {.cpp}
7617 std::vector<
7618 basic_json, // value_type
7619 std::allocator<basic_json> // allocator_type
7620 >
7621 @endcode
7622
7623 #### Limits
7624
7625 [RFC 7159](http://rfc7159.net/rfc7159) specifies:
7626 > An implementation may set limits on the maximum depth of nesting.
7627
Ed Tanousba9f9a62017-10-11 16:40:35 -07007628 In this class, the array's limit of nesting is not explicitly constrained.
Ed Tanous3dac7492017-08-02 13:46:20 -07007629 However, a maximum depth of nesting may be introduced by the compiler or
7630 runtime environment. A theoretical limit can be queried by calling the
7631 @ref max_size function of a JSON array.
7632
7633 #### Storage
7634
7635 Arrays are stored as pointers in a @ref basic_json type. That is, for any
7636 access to array values, a pointer of type `array_t*` must be dereferenced.
7637
7638 @sa @ref object_t -- type for an object value
7639
7640 @since version 1.0.0
7641 */
7642 using array_t = ArrayType<basic_json, AllocatorType<basic_json>>;
7643
7644 /*!
7645 @brief a type for a string
7646
7647 [RFC 7159](http://rfc7159.net/rfc7159) describes JSON strings as follows:
7648 > A string is a sequence of zero or more Unicode characters.
7649
7650 To store objects in C++, a type is defined by the template parameter
7651 described below. Unicode values are split by the JSON class into
7652 byte-sized characters during deserialization.
7653
7654 @tparam StringType the container to store strings (e.g., `std::string`).
7655 Note this container is used for keys/names in objects, see @ref object_t.
7656
7657 #### Default type
7658
7659 With the default values for @a StringType (`std::string`), the default
7660 value for @a string_t is:
7661
7662 @code {.cpp}
7663 std::string
7664 @endcode
7665
7666 #### Encoding
7667
7668 Strings are stored in UTF-8 encoding. Therefore, functions like
7669 `std::string::size()` or `std::string::length()` return the number of
7670 bytes in the string rather than the number of characters or glyphs.
7671
7672 #### String comparison
7673
7674 [RFC 7159](http://rfc7159.net/rfc7159) states:
7675 > Software implementations are typically required to test names of object
7676 > members for equality. Implementations that transform the textual
7677 > representation into sequences of Unicode code units and then perform the
7678 > comparison numerically, code unit by code unit, are interoperable in the
7679 > sense that implementations will agree in all cases on equality or
7680 > inequality of two strings. For example, implementations that compare
7681 > strings with escaped characters unconverted may incorrectly find that
7682 > `"a\\b"` and `"a\u005Cb"` are not equal.
7683
7684 This implementation is interoperable as it does compare strings code unit
7685 by code unit.
7686
7687 #### Storage
7688
7689 String values are stored as pointers in a @ref basic_json type. That is,
7690 for any access to string values, a pointer of type `string_t*` must be
7691 dereferenced.
7692
7693 @since version 1.0.0
7694 */
7695 using string_t = StringType;
7696
7697 /*!
7698 @brief a type for a boolean
7699
7700 [RFC 7159](http://rfc7159.net/rfc7159) implicitly describes a boolean as a
7701 type which differentiates the two literals `true` and `false`.
7702
7703 To store objects in C++, a type is defined by the template parameter @a
7704 BooleanType which chooses the type to use.
7705
7706 #### Default type
7707
7708 With the default values for @a BooleanType (`bool`), the default value for
7709 @a boolean_t is:
7710
7711 @code {.cpp}
7712 bool
7713 @endcode
7714
7715 #### Storage
7716
7717 Boolean values are stored directly inside a @ref basic_json type.
7718
7719 @since version 1.0.0
7720 */
7721 using boolean_t = BooleanType;
7722
7723 /*!
7724 @brief a type for a number (integer)
7725
7726 [RFC 7159](http://rfc7159.net/rfc7159) describes numbers as follows:
7727 > The representation of numbers is similar to that used in most
7728 > programming languages. A number is represented in base 10 using decimal
7729 > digits. It contains an integer component that may be prefixed with an
7730 > optional minus sign, which may be followed by a fraction part and/or an
7731 > exponent part. Leading zeros are not allowed. (...) Numeric values that
7732 > cannot be represented in the grammar below (such as Infinity and NaN)
7733 > are not permitted.
7734
7735 This description includes both integer and floating-point numbers.
7736 However, C++ allows more precise storage if it is known whether the number
7737 is a signed integer, an unsigned integer or a floating-point number.
7738 Therefore, three different types, @ref number_integer_t, @ref
7739 number_unsigned_t and @ref number_float_t are used.
7740
7741 To store integer numbers in C++, a type is defined by the template
7742 parameter @a NumberIntegerType which chooses the type to use.
7743
7744 #### Default type
7745
7746 With the default values for @a NumberIntegerType (`int64_t`), the default
7747 value for @a number_integer_t is:
7748
7749 @code {.cpp}
7750 int64_t
7751 @endcode
7752
7753 #### Default behavior
7754
7755 - The restrictions about leading zeros is not enforced in C++. Instead,
7756 leading zeros in integer literals lead to an interpretation as octal
7757 number. Internally, the value will be stored as decimal number. For
7758 instance, the C++ integer literal `010` will be serialized to `8`.
7759 During deserialization, leading zeros yield an error.
7760 - Not-a-number (NaN) values will be serialized to `null`.
7761
7762 #### Limits
7763
7764 [RFC 7159](http://rfc7159.net/rfc7159) specifies:
7765 > An implementation may set limits on the range and precision of numbers.
7766
7767 When the default type is used, the maximal integer number that can be
7768 stored is `9223372036854775807` (INT64_MAX) and the minimal integer number
7769 that can be stored is `-9223372036854775808` (INT64_MIN). Integer numbers
7770 that are out of range will yield over/underflow when used in a
7771 constructor. During deserialization, too large or small integer numbers
7772 will be automatically be stored as @ref number_unsigned_t or @ref
7773 number_float_t.
7774
7775 [RFC 7159](http://rfc7159.net/rfc7159) further states:
7776 > Note that when such software is used, numbers that are integers and are
7777 > in the range \f$[-2^{53}+1, 2^{53}-1]\f$ are interoperable in the sense
7778 > that implementations will agree exactly on their numeric values.
7779
7780 As this range is a subrange of the exactly supported range [INT64_MIN,
7781 INT64_MAX], this class's integer type is interoperable.
7782
7783 #### Storage
7784
7785 Integer number values are stored directly inside a @ref basic_json type.
7786
7787 @sa @ref number_float_t -- type for number values (floating-point)
7788
7789 @sa @ref number_unsigned_t -- type for number values (unsigned integer)
7790
7791 @since version 1.0.0
7792 */
7793 using number_integer_t = NumberIntegerType;
7794
7795 /*!
7796 @brief a type for a number (unsigned)
7797
7798 [RFC 7159](http://rfc7159.net/rfc7159) describes numbers as follows:
7799 > The representation of numbers is similar to that used in most
7800 > programming languages. A number is represented in base 10 using decimal
7801 > digits. It contains an integer component that may be prefixed with an
7802 > optional minus sign, which may be followed by a fraction part and/or an
7803 > exponent part. Leading zeros are not allowed. (...) Numeric values that
7804 > cannot be represented in the grammar below (such as Infinity and NaN)
7805 > are not permitted.
7806
7807 This description includes both integer and floating-point numbers.
7808 However, C++ allows more precise storage if it is known whether the number
7809 is a signed integer, an unsigned integer or a floating-point number.
7810 Therefore, three different types, @ref number_integer_t, @ref
7811 number_unsigned_t and @ref number_float_t are used.
7812
7813 To store unsigned integer numbers in C++, a type is defined by the
7814 template parameter @a NumberUnsignedType which chooses the type to use.
7815
7816 #### Default type
7817
7818 With the default values for @a NumberUnsignedType (`uint64_t`), the
7819 default value for @a number_unsigned_t is:
7820
7821 @code {.cpp}
7822 uint64_t
7823 @endcode
7824
7825 #### Default behavior
7826
7827 - The restrictions about leading zeros is not enforced in C++. Instead,
7828 leading zeros in integer literals lead to an interpretation as octal
7829 number. Internally, the value will be stored as decimal number. For
7830 instance, the C++ integer literal `010` will be serialized to `8`.
7831 During deserialization, leading zeros yield an error.
7832 - Not-a-number (NaN) values will be serialized to `null`.
7833
7834 #### Limits
7835
7836 [RFC 7159](http://rfc7159.net/rfc7159) specifies:
7837 > An implementation may set limits on the range and precision of numbers.
7838
7839 When the default type is used, the maximal integer number that can be
7840 stored is `18446744073709551615` (UINT64_MAX) and the minimal integer
7841 number that can be stored is `0`. Integer numbers that are out of range
7842 will yield over/underflow when used in a constructor. During
7843 deserialization, too large or small integer numbers will be automatically
7844 be stored as @ref number_integer_t or @ref number_float_t.
7845
7846 [RFC 7159](http://rfc7159.net/rfc7159) further states:
7847 > Note that when such software is used, numbers that are integers and are
7848 > in the range \f$[-2^{53}+1, 2^{53}-1]\f$ are interoperable in the sense
7849 > that implementations will agree exactly on their numeric values.
7850
7851 As this range is a subrange (when considered in conjunction with the
7852 number_integer_t type) of the exactly supported range [0, UINT64_MAX],
7853 this class's integer type is interoperable.
7854
7855 #### Storage
7856
7857 Integer number values are stored directly inside a @ref basic_json type.
7858
7859 @sa @ref number_float_t -- type for number values (floating-point)
7860 @sa @ref number_integer_t -- type for number values (integer)
7861
7862 @since version 2.0.0
7863 */
7864 using number_unsigned_t = NumberUnsignedType;
7865
7866 /*!
7867 @brief a type for a number (floating-point)
7868
7869 [RFC 7159](http://rfc7159.net/rfc7159) describes numbers as follows:
7870 > The representation of numbers is similar to that used in most
7871 > programming languages. A number is represented in base 10 using decimal
7872 > digits. It contains an integer component that may be prefixed with an
7873 > optional minus sign, which may be followed by a fraction part and/or an
7874 > exponent part. Leading zeros are not allowed. (...) Numeric values that
7875 > cannot be represented in the grammar below (such as Infinity and NaN)
7876 > are not permitted.
7877
7878 This description includes both integer and floating-point numbers.
7879 However, C++ allows more precise storage if it is known whether the number
7880 is a signed integer, an unsigned integer or a floating-point number.
7881 Therefore, three different types, @ref number_integer_t, @ref
7882 number_unsigned_t and @ref number_float_t are used.
7883
7884 To store floating-point numbers in C++, a type is defined by the template
7885 parameter @a NumberFloatType which chooses the type to use.
7886
7887 #### Default type
7888
7889 With the default values for @a NumberFloatType (`double`), the default
7890 value for @a number_float_t is:
7891
7892 @code {.cpp}
7893 double
7894 @endcode
7895
7896 #### Default behavior
7897
7898 - The restrictions about leading zeros is not enforced in C++. Instead,
7899 leading zeros in floating-point literals will be ignored. Internally,
7900 the value will be stored as decimal number. For instance, the C++
7901 floating-point literal `01.2` will be serialized to `1.2`. During
7902 deserialization, leading zeros yield an error.
7903 - Not-a-number (NaN) values will be serialized to `null`.
7904
7905 #### Limits
7906
7907 [RFC 7159](http://rfc7159.net/rfc7159) states:
7908 > This specification allows implementations to set limits on the range and
7909 > precision of numbers accepted. Since software that implements IEEE
7910 > 754-2008 binary64 (double precision) numbers is generally available and
7911 > widely used, good interoperability can be achieved by implementations
7912 > that expect no more precision or range than these provide, in the sense
7913 > that implementations will approximate JSON numbers within the expected
7914 > precision.
7915
7916 This implementation does exactly follow this approach, as it uses double
7917 precision floating-point numbers. Note values smaller than
7918 `-1.79769313486232e+308` and values greater than `1.79769313486232e+308`
7919 will be stored as NaN internally and be serialized to `null`.
7920
7921 #### Storage
7922
7923 Floating-point number values are stored directly inside a @ref basic_json
7924 type.
7925
7926 @sa @ref number_integer_t -- type for number values (integer)
7927
7928 @sa @ref number_unsigned_t -- type for number values (unsigned integer)
7929
7930 @since version 1.0.0
7931 */
7932 using number_float_t = NumberFloatType;
7933
7934 /// @}
7935
7936 private:
7937
7938 /// helper for exception-safe object creation
7939 template<typename T, typename... Args>
7940 static T* create(Args&& ... args)
7941 {
7942 AllocatorType<T> alloc;
7943 auto deleter = [&](T * object)
7944 {
7945 alloc.deallocate(object, 1);
7946 };
7947 std::unique_ptr<T, decltype(deleter)> object(alloc.allocate(1), deleter);
7948 alloc.construct(object.get(), std::forward<Args>(args)...);
7949 assert(object != nullptr);
7950 return object.release();
7951 }
7952
7953 ////////////////////////
7954 // JSON value storage //
7955 ////////////////////////
7956
7957 /*!
7958 @brief a JSON value
7959
7960 The actual storage for a JSON value of the @ref basic_json class. This
7961 union combines the different storage types for the JSON value types
7962 defined in @ref value_t.
7963
7964 JSON type | value_t type | used type
7965 --------- | --------------- | ------------------------
7966 object | object | pointer to @ref object_t
7967 array | array | pointer to @ref array_t
7968 string | string | pointer to @ref string_t
7969 boolean | boolean | @ref boolean_t
7970 number | number_integer | @ref number_integer_t
7971 number | number_unsigned | @ref number_unsigned_t
7972 number | number_float | @ref number_float_t
7973 null | null | *no value is stored*
7974
7975 @note Variable-length types (objects, arrays, and strings) are stored as
7976 pointers. The size of the union should not exceed 64 bits if the default
7977 value types are used.
7978
7979 @since version 1.0.0
7980 */
7981 union json_value
7982 {
7983 /// object (stored with pointer to save storage)
7984 object_t* object;
7985 /// array (stored with pointer to save storage)
7986 array_t* array;
7987 /// string (stored with pointer to save storage)
7988 string_t* string;
7989 /// boolean
7990 boolean_t boolean;
7991 /// number (integer)
7992 number_integer_t number_integer;
7993 /// number (unsigned integer)
7994 number_unsigned_t number_unsigned;
7995 /// number (floating-point)
7996 number_float_t number_float;
7997
7998 /// default constructor (for null values)
7999 json_value() = default;
8000 /// constructor for booleans
8001 json_value(boolean_t v) noexcept : boolean(v) {}
8002 /// constructor for numbers (integer)
8003 json_value(number_integer_t v) noexcept : number_integer(v) {}
8004 /// constructor for numbers (unsigned)
8005 json_value(number_unsigned_t v) noexcept : number_unsigned(v) {}
8006 /// constructor for numbers (floating-point)
8007 json_value(number_float_t v) noexcept : number_float(v) {}
8008 /// constructor for empty values of a given type
8009 json_value(value_t t)
8010 {
8011 switch (t)
8012 {
8013 case value_t::object:
8014 {
8015 object = create<object_t>();
8016 break;
8017 }
8018
8019 case value_t::array:
8020 {
8021 array = create<array_t>();
8022 break;
8023 }
8024
8025 case value_t::string:
8026 {
8027 string = create<string_t>("");
8028 break;
8029 }
8030
8031 case value_t::boolean:
8032 {
8033 boolean = boolean_t(false);
8034 break;
8035 }
8036
8037 case value_t::number_integer:
8038 {
8039 number_integer = number_integer_t(0);
8040 break;
8041 }
8042
8043 case value_t::number_unsigned:
8044 {
8045 number_unsigned = number_unsigned_t(0);
8046 break;
8047 }
8048
8049 case value_t::number_float:
8050 {
8051 number_float = number_float_t(0.0);
8052 break;
8053 }
8054
8055 case value_t::null:
8056 {
8057 break;
8058 }
8059
8060 default:
8061 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07008062 if (JSON_UNLIKELY(t == value_t::null))
Ed Tanous3dac7492017-08-02 13:46:20 -07008063 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07008064 JSON_THROW(other_error::create(500, "961c151d2e87f2686a955a9be24d316f1362bf21 2.1.1")); // LCOV_EXCL_LINE
Ed Tanous3dac7492017-08-02 13:46:20 -07008065 }
8066 break;
8067 }
8068 }
8069 }
8070
8071 /// constructor for strings
8072 json_value(const string_t& value)
8073 {
8074 string = create<string_t>(value);
8075 }
8076
Ed Tanousba9f9a62017-10-11 16:40:35 -07008077 /// constructor for rvalue strings
8078 json_value(string_t&& value)
8079 {
8080 string = create<string_t>(std::move(value));
8081 }
8082
Ed Tanous3dac7492017-08-02 13:46:20 -07008083 /// constructor for objects
8084 json_value(const object_t& value)
8085 {
8086 object = create<object_t>(value);
8087 }
8088
Ed Tanousba9f9a62017-10-11 16:40:35 -07008089 /// constructor for rvalue objects
8090 json_value(object_t&& value)
8091 {
8092 object = create<object_t>(std::move(value));
8093 }
8094
Ed Tanous3dac7492017-08-02 13:46:20 -07008095 /// constructor for arrays
8096 json_value(const array_t& value)
8097 {
8098 array = create<array_t>(value);
8099 }
Ed Tanousba9f9a62017-10-11 16:40:35 -07008100
8101 /// constructor for rvalue arrays
8102 json_value(array_t&& value)
8103 {
8104 array = create<array_t>(std::move(value));
8105 }
8106
8107 void destroy(value_t t)
8108 {
8109 switch (t)
8110 {
8111 case value_t::object:
8112 {
8113 AllocatorType<object_t> alloc;
8114 alloc.destroy(object);
8115 alloc.deallocate(object, 1);
8116 break;
8117 }
8118
8119 case value_t::array:
8120 {
8121 AllocatorType<array_t> alloc;
8122 alloc.destroy(array);
8123 alloc.deallocate(array, 1);
8124 break;
8125 }
8126
8127 case value_t::string:
8128 {
8129 AllocatorType<string_t> alloc;
8130 alloc.destroy(string);
8131 alloc.deallocate(string, 1);
8132 break;
8133 }
8134
8135 default:
8136 {
8137 break;
8138 }
8139 }
8140 }
Ed Tanous3dac7492017-08-02 13:46:20 -07008141 };
8142
8143 /*!
8144 @brief checks the class invariants
8145
8146 This function asserts the class invariants. It needs to be called at the
8147 end of every constructor to make sure that created objects respect the
8148 invariant. Furthermore, it has to be called each time the type of a JSON
8149 value is changed, because the invariant expresses a relationship between
8150 @a m_type and @a m_value.
8151 */
8152 void assert_invariant() const
8153 {
8154 assert(m_type != value_t::object or m_value.object != nullptr);
8155 assert(m_type != value_t::array or m_value.array != nullptr);
8156 assert(m_type != value_t::string or m_value.string != nullptr);
8157 }
8158
8159 public:
8160 //////////////////////////
8161 // JSON parser callback //
8162 //////////////////////////
8163
Ed Tanousba9f9a62017-10-11 16:40:35 -07008164 using parse_event_t = typename parser::parse_event_t;
Ed Tanous3dac7492017-08-02 13:46:20 -07008165
8166 /*!
8167 @brief per-element parser callback type
8168
8169 With a parser callback function, the result of parsing a JSON text can be
8170 influenced. When passed to @ref parse(std::istream&, const
8171 parser_callback_t) or @ref parse(const CharT, const parser_callback_t),
8172 it is called on certain events (passed as @ref parse_event_t via parameter
8173 @a event) with a set recursion depth @a depth and context JSON value
8174 @a parsed. The return value of the callback function is a boolean
8175 indicating whether the element that emitted the callback shall be kept or
8176 not.
8177
8178 We distinguish six scenarios (determined by the event type) in which the
8179 callback function can be called. The following table describes the values
8180 of the parameters @a depth, @a event, and @a parsed.
8181
8182 parameter @a event | description | parameter @a depth | parameter @a parsed
8183 ------------------ | ----------- | ------------------ | -------------------
8184 parse_event_t::object_start | the parser read `{` and started to process a JSON object | depth of the parent of the JSON object | a JSON value with type discarded
8185 parse_event_t::key | the parser read a key of a value in an object | depth of the currently parsed JSON object | a JSON string containing the key
8186 parse_event_t::object_end | the parser read `}` and finished processing a JSON object | depth of the parent of the JSON object | the parsed JSON object
8187 parse_event_t::array_start | the parser read `[` and started to process a JSON array | depth of the parent of the JSON array | a JSON value with type discarded
8188 parse_event_t::array_end | the parser read `]` and finished processing a JSON array | depth of the parent of the JSON array | the parsed JSON array
8189 parse_event_t::value | the parser finished reading a JSON value | depth of the value | the parsed JSON value
8190
8191 @image html callback_events.png "Example when certain parse events are triggered"
8192
8193 Discarding a value (i.e., returning `false`) has different effects
8194 depending on the context in which function was called:
8195
8196 - Discarded values in structured types are skipped. That is, the parser
8197 will behave as if the discarded value was never read.
8198 - In case a value outside a structured type is skipped, it is replaced
8199 with `null`. This case happens if the top-level element is skipped.
8200
8201 @param[in] depth the depth of the recursion during parsing
8202
8203 @param[in] event an event of type parse_event_t indicating the context in
8204 the callback function has been called
8205
8206 @param[in,out] parsed the current intermediate parse result; note that
8207 writing to this value has no effect for parse_event_t::key events
8208
8209 @return Whether the JSON value which called the function during parsing
8210 should be kept (`true`) or not (`false`). In the latter case, it is either
8211 skipped completely or replaced by an empty discarded object.
8212
8213 @sa @ref parse(std::istream&, parser_callback_t) or
8214 @ref parse(const CharT, const parser_callback_t) for examples
8215
8216 @since version 1.0.0
8217 */
Ed Tanousba9f9a62017-10-11 16:40:35 -07008218 using parser_callback_t = typename parser::parser_callback_t;
Ed Tanous3dac7492017-08-02 13:46:20 -07008219
8220
8221 //////////////////
8222 // constructors //
8223 //////////////////
8224
8225 /// @name constructors and destructors
8226 /// Constructors of class @ref basic_json, copy/move constructor, copy
8227 /// assignment, static functions creating objects, and the destructor.
8228 /// @{
8229
8230 /*!
8231 @brief create an empty value with a given type
8232
8233 Create an empty JSON value with a given type. The value will be default
8234 initialized with an empty value which depends on the type:
8235
8236 Value type | initial value
8237 ----------- | -------------
8238 null | `null`
8239 boolean | `false`
8240 string | `""`
8241 number | `0`
8242 object | `{}`
8243 array | `[]`
8244
Ed Tanousba9f9a62017-10-11 16:40:35 -07008245 @param[in] v the type of the value to create
Ed Tanous3dac7492017-08-02 13:46:20 -07008246
8247 @complexity Constant.
8248
Ed Tanousba9f9a62017-10-11 16:40:35 -07008249 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
8250 changes to any JSON value.
Ed Tanous3dac7492017-08-02 13:46:20 -07008251
8252 @liveexample{The following code shows the constructor for different @ref
8253 value_t values,basic_json__value_t}
8254
Ed Tanousba9f9a62017-10-11 16:40:35 -07008255 @sa @ref clear() -- restores the postcondition of this constructor
8256
Ed Tanous3dac7492017-08-02 13:46:20 -07008257 @since version 1.0.0
8258 */
Ed Tanousba9f9a62017-10-11 16:40:35 -07008259 basic_json(const value_t v)
8260 : m_type(v), m_value(v)
Ed Tanous3dac7492017-08-02 13:46:20 -07008261 {
8262 assert_invariant();
8263 }
8264
8265 /*!
8266 @brief create a null object
8267
8268 Create a `null` JSON value. It either takes a null pointer as parameter
8269 (explicitly creating `null`) or no parameter (implicitly creating `null`).
8270 The passed null pointer itself is not read -- it is only used to choose
8271 the right constructor.
8272
8273 @complexity Constant.
8274
8275 @exceptionsafety No-throw guarantee: this constructor never throws
8276 exceptions.
8277
8278 @liveexample{The following code shows the constructor with and without a
8279 null pointer parameter.,basic_json__nullptr_t}
8280
8281 @since version 1.0.0
8282 */
8283 basic_json(std::nullptr_t = nullptr) noexcept
8284 : basic_json(value_t::null)
8285 {
8286 assert_invariant();
8287 }
8288
8289 /*!
8290 @brief create a JSON value
8291
8292 This is a "catch all" constructor for all compatible JSON types; that is,
8293 types for which a `to_json()` method exsits. The constructor forwards the
8294 parameter @a val to that method (to `json_serializer<U>::to_json` method
8295 with `U = uncvref_t<CompatibleType>`, to be exact).
8296
8297 Template type @a CompatibleType includes, but is not limited to, the
8298 following types:
8299 - **arrays**: @ref array_t and all kinds of compatible containers such as
8300 `std::vector`, `std::deque`, `std::list`, `std::forward_list`,
Ed Tanousba9f9a62017-10-11 16:40:35 -07008301 `std::array`, `std::valarray`, `std::set`, `std::unordered_set`,
8302 `std::multiset`, and `std::unordered_multiset` with a `value_type` from
8303 which a @ref basic_json value can be constructed.
Ed Tanous3dac7492017-08-02 13:46:20 -07008304 - **objects**: @ref object_t and all kinds of compatible associative
8305 containers such as `std::map`, `std::unordered_map`, `std::multimap`,
8306 and `std::unordered_multimap` with a `key_type` compatible to
8307 @ref string_t and a `value_type` from which a @ref basic_json value can
8308 be constructed.
8309 - **strings**: @ref string_t, string literals, and all compatible string
8310 containers can be used.
8311 - **numbers**: @ref number_integer_t, @ref number_unsigned_t,
8312 @ref number_float_t, and all convertible number types such as `int`,
8313 `size_t`, `int64_t`, `float` or `double` can be used.
8314 - **boolean**: @ref boolean_t / `bool` can be used.
8315
8316 See the examples below.
8317
8318 @tparam CompatibleType a type such that:
8319 - @a CompatibleType is not derived from `std::istream`,
8320 - @a CompatibleType is not @ref basic_json (to avoid hijacking copy/move
8321 constructors),
8322 - @a CompatibleType is not a @ref basic_json nested type (e.g.,
8323 @ref json_pointer, @ref iterator, etc ...)
8324 - @ref @ref json_serializer<U> has a
8325 `to_json(basic_json_t&, CompatibleType&&)` method
8326
8327 @tparam U = `uncvref_t<CompatibleType>`
8328
Ed Tanousba9f9a62017-10-11 16:40:35 -07008329 @param[in] val the value to be forwarded to the respective constructor
Ed Tanous3dac7492017-08-02 13:46:20 -07008330
8331 @complexity Usually linear in the size of the passed @a val, also
8332 depending on the implementation of the called `to_json()`
8333 method.
8334
Ed Tanousba9f9a62017-10-11 16:40:35 -07008335 @exceptionsafety Depends on the called constructor. For types directly
8336 supported by the library (i.e., all types for which no `to_json()` function
8337 was provided), strong guarantee holds: if an exception is thrown, there are
8338 no changes to any JSON value.
Ed Tanous3dac7492017-08-02 13:46:20 -07008339
8340 @liveexample{The following code shows the constructor with several
8341 compatible types.,basic_json__CompatibleType}
8342
8343 @since version 2.1.0
8344 */
8345 template<typename CompatibleType, typename U = detail::uncvref_t<CompatibleType>,
8346 detail::enable_if_t<not std::is_base_of<std::istream, U>::value and
8347 not std::is_same<U, basic_json_t>::value and
8348 not detail::is_basic_json_nested_type<
8349 basic_json_t, U>::value and
8350 detail::has_to_json<basic_json, U>::value,
8351 int> = 0>
8352 basic_json(CompatibleType && val) noexcept(noexcept(JSONSerializer<U>::to_json(
8353 std::declval<basic_json_t&>(), std::forward<CompatibleType>(val))))
8354 {
8355 JSONSerializer<U>::to_json(*this, std::forward<CompatibleType>(val));
8356 assert_invariant();
8357 }
8358
8359 /*!
8360 @brief create a container (array or object) from an initializer list
8361
8362 Creates a JSON value of type array or object from the passed initializer
8363 list @a init. In case @a type_deduction is `true` (default), the type of
8364 the JSON value to be created is deducted from the initializer list @a init
8365 according to the following rules:
8366
8367 1. If the list is empty, an empty JSON object value `{}` is created.
8368 2. If the list consists of pairs whose first element is a string, a JSON
8369 object value is created where the first elements of the pairs are
8370 treated as keys and the second elements are as values.
8371 3. In all other cases, an array is created.
8372
8373 The rules aim to create the best fit between a C++ initializer list and
8374 JSON values. The rationale is as follows:
8375
8376 1. The empty initializer list is written as `{}` which is exactly an empty
8377 JSON object.
Ed Tanousba9f9a62017-10-11 16:40:35 -07008378 2. C++ has no way of describing mapped types other than to list a list of
Ed Tanous3dac7492017-08-02 13:46:20 -07008379 pairs. As JSON requires that keys must be of type string, rule 2 is the
8380 weakest constraint one can pose on initializer lists to interpret them
8381 as an object.
8382 3. In all other cases, the initializer list could not be interpreted as
8383 JSON object type, so interpreting it as JSON array type is safe.
8384
8385 With the rules described above, the following JSON values cannot be
8386 expressed by an initializer list:
8387
Ed Tanousba9f9a62017-10-11 16:40:35 -07008388 - the empty array (`[]`): use @ref array(initializer_list_t)
Ed Tanous3dac7492017-08-02 13:46:20 -07008389 with an empty initializer list in this case
8390 - arrays whose elements satisfy rule 2: use @ref
Ed Tanousba9f9a62017-10-11 16:40:35 -07008391 array(initializer_list_t) with the same initializer list
Ed Tanous3dac7492017-08-02 13:46:20 -07008392 in this case
8393
8394 @note When used without parentheses around an empty initializer list, @ref
8395 basic_json() is called instead of this function, yielding the JSON null
8396 value.
8397
8398 @param[in] init initializer list with JSON values
8399
8400 @param[in] type_deduction internal parameter; when set to `true`, the type
8401 of the JSON value is deducted from the initializer list @a init; when set
8402 to `false`, the type provided via @a manual_type is forced. This mode is
Ed Tanousba9f9a62017-10-11 16:40:35 -07008403 used by the functions @ref array(initializer_list_t) and
8404 @ref object(initializer_list_t).
Ed Tanous3dac7492017-08-02 13:46:20 -07008405
8406 @param[in] manual_type internal parameter; when @a type_deduction is set
8407 to `false`, the created JSON value will use the provided type (only @ref
8408 value_t::array and @ref value_t::object are valid); when @a type_deduction
8409 is set to `true`, this parameter has no effect
8410
Ed Tanousba9f9a62017-10-11 16:40:35 -07008411 @throw type_error.301 if @a type_deduction is `false`, @a manual_type is
8412 `value_t::object`, but @a init contains an element which is not a pair
8413 whose first element is a string. In this case, the constructor could not
8414 create an object. If @a type_deduction would have be `true`, an array
8415 would have been created. See @ref object(initializer_list_t)
8416 for an example.
Ed Tanous3dac7492017-08-02 13:46:20 -07008417
8418 @complexity Linear in the size of the initializer list @a init.
8419
Ed Tanousba9f9a62017-10-11 16:40:35 -07008420 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
8421 changes to any JSON value.
8422
Ed Tanous3dac7492017-08-02 13:46:20 -07008423 @liveexample{The example below shows how JSON values are created from
8424 initializer lists.,basic_json__list_init_t}
8425
Ed Tanousba9f9a62017-10-11 16:40:35 -07008426 @sa @ref array(initializer_list_t) -- create a JSON array
Ed Tanous3dac7492017-08-02 13:46:20 -07008427 value from an initializer list
Ed Tanousba9f9a62017-10-11 16:40:35 -07008428 @sa @ref object(initializer_list_t) -- create a JSON object
Ed Tanous3dac7492017-08-02 13:46:20 -07008429 value from an initializer list
8430
8431 @since version 1.0.0
8432 */
Ed Tanousba9f9a62017-10-11 16:40:35 -07008433 basic_json(initializer_list_t init,
Ed Tanous3dac7492017-08-02 13:46:20 -07008434 bool type_deduction = true,
8435 value_t manual_type = value_t::array)
8436 {
8437 // check if each element is an array with two elements whose first
8438 // element is a string
8439 bool is_an_object = std::all_of(init.begin(), init.end(),
Ed Tanousba9f9a62017-10-11 16:40:35 -07008440 [](const detail::json_ref<basic_json>& element_ref)
Ed Tanous3dac7492017-08-02 13:46:20 -07008441 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07008442 return (element_ref->is_array() and element_ref->size() == 2 and (*element_ref)[0].is_string());
Ed Tanous3dac7492017-08-02 13:46:20 -07008443 });
8444
8445 // adjust type if type deduction is not wanted
8446 if (not type_deduction)
8447 {
8448 // if array is wanted, do not create an object though possible
8449 if (manual_type == value_t::array)
8450 {
8451 is_an_object = false;
8452 }
8453
8454 // if object is wanted but impossible, throw an exception
Ed Tanousba9f9a62017-10-11 16:40:35 -07008455 if (JSON_UNLIKELY(manual_type == value_t::object and not is_an_object))
Ed Tanous3dac7492017-08-02 13:46:20 -07008456 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07008457 JSON_THROW(type_error::create(301, "cannot create object from initializer list"));
Ed Tanous3dac7492017-08-02 13:46:20 -07008458 }
8459 }
8460
8461 if (is_an_object)
8462 {
8463 // the initializer list is a list of pairs -> create object
8464 m_type = value_t::object;
8465 m_value = value_t::object;
8466
Ed Tanousba9f9a62017-10-11 16:40:35 -07008467 std::for_each(init.begin(), init.end(), [this](const detail::json_ref<basic_json>& element_ref)
Ed Tanous3dac7492017-08-02 13:46:20 -07008468 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07008469 auto element = element_ref.moved_or_copied();
8470 m_value.object->emplace(
8471 std::move(*((*element.m_value.array)[0].m_value.string)),
8472 std::move((*element.m_value.array)[1]));
Ed Tanous3dac7492017-08-02 13:46:20 -07008473 });
8474 }
8475 else
8476 {
8477 // the initializer list describes an array -> create array
8478 m_type = value_t::array;
Ed Tanousba9f9a62017-10-11 16:40:35 -07008479 m_value.array = create<array_t>(init.begin(), init.end());
Ed Tanous3dac7492017-08-02 13:46:20 -07008480 }
8481
8482 assert_invariant();
8483 }
8484
8485 /*!
8486 @brief explicitly create an array from an initializer list
8487
8488 Creates a JSON array value from a given initializer list. That is, given a
8489 list of values `a, b, c`, creates the JSON value `[a, b, c]`. If the
8490 initializer list is empty, the empty array `[]` is created.
8491
8492 @note This function is only needed to express two edge cases that cannot
8493 be realized with the initializer list constructor (@ref
Ed Tanousba9f9a62017-10-11 16:40:35 -07008494 basic_json(initializer_list_t, bool, value_t)). These cases
Ed Tanous3dac7492017-08-02 13:46:20 -07008495 are:
8496 1. creating an array whose elements are all pairs whose first element is a
8497 string -- in this case, the initializer list constructor would create an
8498 object, taking the first elements as keys
8499 2. creating an empty array -- passing the empty initializer list to the
8500 initializer list constructor yields an empty object
8501
8502 @param[in] init initializer list with JSON values to create an array from
8503 (optional)
8504
8505 @return JSON array value
8506
8507 @complexity Linear in the size of @a init.
8508
Ed Tanousba9f9a62017-10-11 16:40:35 -07008509 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
8510 changes to any JSON value.
8511
Ed Tanous3dac7492017-08-02 13:46:20 -07008512 @liveexample{The following code shows an example for the `array`
8513 function.,array}
8514
Ed Tanousba9f9a62017-10-11 16:40:35 -07008515 @sa @ref basic_json(initializer_list_t, bool, value_t) --
Ed Tanous3dac7492017-08-02 13:46:20 -07008516 create a JSON value from an initializer list
Ed Tanousba9f9a62017-10-11 16:40:35 -07008517 @sa @ref object(initializer_list_t) -- create a JSON object
Ed Tanous3dac7492017-08-02 13:46:20 -07008518 value from an initializer list
8519
8520 @since version 1.0.0
8521 */
Ed Tanousba9f9a62017-10-11 16:40:35 -07008522 static basic_json array(initializer_list_t init = {})
Ed Tanous3dac7492017-08-02 13:46:20 -07008523 {
8524 return basic_json(init, false, value_t::array);
8525 }
8526
8527 /*!
8528 @brief explicitly create an object from an initializer list
8529
8530 Creates a JSON object value from a given initializer list. The initializer
8531 lists elements must be pairs, and their first elements must be strings. If
8532 the initializer list is empty, the empty object `{}` is created.
8533
8534 @note This function is only added for symmetry reasons. In contrast to the
Ed Tanousba9f9a62017-10-11 16:40:35 -07008535 related function @ref array(initializer_list_t), there are
Ed Tanous3dac7492017-08-02 13:46:20 -07008536 no cases which can only be expressed by this function. That is, any
8537 initializer list @a init can also be passed to the initializer list
Ed Tanousba9f9a62017-10-11 16:40:35 -07008538 constructor @ref basic_json(initializer_list_t, bool, value_t).
Ed Tanous3dac7492017-08-02 13:46:20 -07008539
8540 @param[in] init initializer list to create an object from (optional)
8541
8542 @return JSON object value
8543
Ed Tanousba9f9a62017-10-11 16:40:35 -07008544 @throw type_error.301 if @a init is not a list of pairs whose first
8545 elements are strings. In this case, no object can be created. When such a
8546 value is passed to @ref basic_json(initializer_list_t, bool, value_t),
8547 an array would have been created from the passed initializer list @a init.
8548 See example below.
Ed Tanous3dac7492017-08-02 13:46:20 -07008549
8550 @complexity Linear in the size of @a init.
8551
Ed Tanousba9f9a62017-10-11 16:40:35 -07008552 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
8553 changes to any JSON value.
8554
Ed Tanous3dac7492017-08-02 13:46:20 -07008555 @liveexample{The following code shows an example for the `object`
8556 function.,object}
8557
Ed Tanousba9f9a62017-10-11 16:40:35 -07008558 @sa @ref basic_json(initializer_list_t, bool, value_t) --
Ed Tanous3dac7492017-08-02 13:46:20 -07008559 create a JSON value from an initializer list
Ed Tanousba9f9a62017-10-11 16:40:35 -07008560 @sa @ref array(initializer_list_t) -- create a JSON array
Ed Tanous3dac7492017-08-02 13:46:20 -07008561 value from an initializer list
8562
8563 @since version 1.0.0
8564 */
Ed Tanousba9f9a62017-10-11 16:40:35 -07008565 static basic_json object(initializer_list_t init = {})
Ed Tanous3dac7492017-08-02 13:46:20 -07008566 {
8567 return basic_json(init, false, value_t::object);
8568 }
8569
8570 /*!
8571 @brief construct an array with count copies of given value
8572
8573 Constructs a JSON array value by creating @a cnt copies of a passed value.
Ed Tanousba9f9a62017-10-11 16:40:35 -07008574 In case @a cnt is `0`, an empty array is created.
Ed Tanous3dac7492017-08-02 13:46:20 -07008575
8576 @param[in] cnt the number of JSON copies of @a val to create
8577 @param[in] val the JSON value to copy
8578
Ed Tanousba9f9a62017-10-11 16:40:35 -07008579 @post `std::distance(begin(),end()) == cnt` holds.
8580
Ed Tanous3dac7492017-08-02 13:46:20 -07008581 @complexity Linear in @a cnt.
8582
Ed Tanousba9f9a62017-10-11 16:40:35 -07008583 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
8584 changes to any JSON value.
8585
Ed Tanous3dac7492017-08-02 13:46:20 -07008586 @liveexample{The following code shows examples for the @ref
8587 basic_json(size_type\, const basic_json&)
8588 constructor.,basic_json__size_type_basic_json}
8589
8590 @since version 1.0.0
8591 */
8592 basic_json(size_type cnt, const basic_json& val)
8593 : m_type(value_t::array)
8594 {
8595 m_value.array = create<array_t>(cnt, val);
8596 assert_invariant();
8597 }
8598
8599 /*!
8600 @brief construct a JSON container given an iterator range
8601
8602 Constructs the JSON value with the contents of the range `[first, last)`.
8603 The semantics depends on the different types a JSON value can have:
Ed Tanousba9f9a62017-10-11 16:40:35 -07008604 - In case of a null type, invalid_iterator.206 is thrown.
8605 - In case of other primitive types (number, boolean, or string), @a first
8606 must be `begin()` and @a last must be `end()`. In this case, the value is
8607 copied. Otherwise, invalid_iterator.204 is thrown.
Ed Tanous3dac7492017-08-02 13:46:20 -07008608 - In case of structured types (array, object), the constructor behaves as
Ed Tanousba9f9a62017-10-11 16:40:35 -07008609 similar versions for `std::vector` or `std::map`; that is, a JSON array
8610 or object is constructed from the values in the range.
Ed Tanous3dac7492017-08-02 13:46:20 -07008611
8612 @tparam InputIT an input iterator type (@ref iterator or @ref
8613 const_iterator)
8614
8615 @param[in] first begin of the range to copy from (included)
8616 @param[in] last end of the range to copy from (excluded)
8617
8618 @pre Iterators @a first and @a last must be initialized. **This
Ed Tanousba9f9a62017-10-11 16:40:35 -07008619 precondition is enforced with an assertion (see warning).** If
8620 assertions are switched off, a violation of this precondition yields
8621 undefined behavior.
Ed Tanous3dac7492017-08-02 13:46:20 -07008622
Ed Tanousba9f9a62017-10-11 16:40:35 -07008623 @pre Range `[first, last)` is valid. Usually, this precondition cannot be
8624 checked efficiently. Only certain edge cases are detected; see the
8625 description of the exceptions below. A violation of this precondition
8626 yields undefined behavior.
8627
8628 @warning A precondition is enforced with a runtime assertion that will
8629 result in calling `std::abort` if this precondition is not met.
8630 Assertions can be disabled by defining `NDEBUG` at compile time.
8631 See http://en.cppreference.com/w/cpp/error/assert for more
8632 information.
8633
8634 @throw invalid_iterator.201 if iterators @a first and @a last are not
8635 compatible (i.e., do not belong to the same JSON value). In this case,
8636 the range `[first, last)` is undefined.
8637 @throw invalid_iterator.204 if iterators @a first and @a last belong to a
8638 primitive type (number, boolean, or string), but @a first does not point
8639 to the first element any more. In this case, the range `[first, last)` is
8640 undefined. See example code below.
8641 @throw invalid_iterator.206 if iterators @a first and @a last belong to a
8642 null value. In this case, the range `[first, last)` is undefined.
Ed Tanous3dac7492017-08-02 13:46:20 -07008643
8644 @complexity Linear in distance between @a first and @a last.
8645
Ed Tanousba9f9a62017-10-11 16:40:35 -07008646 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
8647 changes to any JSON value.
8648
Ed Tanous3dac7492017-08-02 13:46:20 -07008649 @liveexample{The example below shows several ways to create JSON values by
8650 specifying a subrange with iterators.,basic_json__InputIt_InputIt}
8651
8652 @since version 1.0.0
8653 */
8654 template<class InputIT, typename std::enable_if<
8655 std::is_same<InputIT, typename basic_json_t::iterator>::value or
8656 std::is_same<InputIT, typename basic_json_t::const_iterator>::value, int>::type = 0>
8657 basic_json(InputIT first, InputIT last)
8658 {
8659 assert(first.m_object != nullptr);
8660 assert(last.m_object != nullptr);
8661
8662 // make sure iterator fits the current value
Ed Tanousba9f9a62017-10-11 16:40:35 -07008663 if (JSON_UNLIKELY(first.m_object != last.m_object))
Ed Tanous3dac7492017-08-02 13:46:20 -07008664 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07008665 JSON_THROW(invalid_iterator::create(201, "iterators are not compatible"));
Ed Tanous3dac7492017-08-02 13:46:20 -07008666 }
8667
8668 // copy type from first iterator
8669 m_type = first.m_object->m_type;
8670
8671 // check if iterator range is complete for primitive values
8672 switch (m_type)
8673 {
8674 case value_t::boolean:
8675 case value_t::number_float:
8676 case value_t::number_integer:
8677 case value_t::number_unsigned:
8678 case value_t::string:
8679 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07008680 if (JSON_UNLIKELY(not first.m_it.primitive_iterator.is_begin()
8681 or not last.m_it.primitive_iterator.is_end()))
Ed Tanous3dac7492017-08-02 13:46:20 -07008682 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07008683 JSON_THROW(invalid_iterator::create(204, "iterators out of range"));
Ed Tanous3dac7492017-08-02 13:46:20 -07008684 }
8685 break;
8686 }
8687
8688 default:
Ed Tanous3dac7492017-08-02 13:46:20 -07008689 break;
Ed Tanous3dac7492017-08-02 13:46:20 -07008690 }
8691
8692 switch (m_type)
8693 {
8694 case value_t::number_integer:
8695 {
8696 m_value.number_integer = first.m_object->m_value.number_integer;
8697 break;
8698 }
8699
8700 case value_t::number_unsigned:
8701 {
8702 m_value.number_unsigned = first.m_object->m_value.number_unsigned;
8703 break;
8704 }
8705
8706 case value_t::number_float:
8707 {
8708 m_value.number_float = first.m_object->m_value.number_float;
8709 break;
8710 }
8711
8712 case value_t::boolean:
8713 {
8714 m_value.boolean = first.m_object->m_value.boolean;
8715 break;
8716 }
8717
8718 case value_t::string:
8719 {
8720 m_value = *first.m_object->m_value.string;
8721 break;
8722 }
8723
8724 case value_t::object:
8725 {
8726 m_value.object = create<object_t>(first.m_it.object_iterator,
8727 last.m_it.object_iterator);
8728 break;
8729 }
8730
8731 case value_t::array:
8732 {
8733 m_value.array = create<array_t>(first.m_it.array_iterator,
8734 last.m_it.array_iterator);
8735 break;
8736 }
8737
8738 default:
Ed Tanousba9f9a62017-10-11 16:40:35 -07008739 JSON_THROW(invalid_iterator::create(206, "cannot construct with iterators from " +
8740 std::string(first.m_object->type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07008741 }
8742
8743 assert_invariant();
8744 }
8745
Ed Tanous3dac7492017-08-02 13:46:20 -07008746
8747 ///////////////////////////////////////
8748 // other constructors and destructor //
8749 ///////////////////////////////////////
8750
Ed Tanousba9f9a62017-10-11 16:40:35 -07008751 /// @private
8752 basic_json(const detail::json_ref<basic_json>& ref)
8753 : basic_json(ref.moved_or_copied())
8754 {}
8755
Ed Tanous3dac7492017-08-02 13:46:20 -07008756 /*!
8757 @brief copy constructor
8758
8759 Creates a copy of a given JSON value.
8760
8761 @param[in] other the JSON value to copy
8762
Ed Tanousba9f9a62017-10-11 16:40:35 -07008763 @post `*this == other`
8764
Ed Tanous3dac7492017-08-02 13:46:20 -07008765 @complexity Linear in the size of @a other.
8766
Ed Tanousba9f9a62017-10-11 16:40:35 -07008767 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
8768 changes to any JSON value.
8769
Ed Tanous3dac7492017-08-02 13:46:20 -07008770 @requirement This function helps `basic_json` satisfying the
8771 [Container](http://en.cppreference.com/w/cpp/concept/Container)
8772 requirements:
8773 - The complexity is linear.
8774 - As postcondition, it holds: `other == basic_json(other)`.
8775
Ed Tanous3dac7492017-08-02 13:46:20 -07008776 @liveexample{The following code shows an example for the copy
8777 constructor.,basic_json__basic_json}
8778
8779 @since version 1.0.0
8780 */
8781 basic_json(const basic_json& other)
8782 : m_type(other.m_type)
8783 {
8784 // check of passed value is valid
8785 other.assert_invariant();
8786
8787 switch (m_type)
8788 {
8789 case value_t::object:
8790 {
8791 m_value = *other.m_value.object;
8792 break;
8793 }
8794
8795 case value_t::array:
8796 {
8797 m_value = *other.m_value.array;
8798 break;
8799 }
8800
8801 case value_t::string:
8802 {
8803 m_value = *other.m_value.string;
8804 break;
8805 }
8806
8807 case value_t::boolean:
8808 {
8809 m_value = other.m_value.boolean;
8810 break;
8811 }
8812
8813 case value_t::number_integer:
8814 {
8815 m_value = other.m_value.number_integer;
8816 break;
8817 }
8818
8819 case value_t::number_unsigned:
8820 {
8821 m_value = other.m_value.number_unsigned;
8822 break;
8823 }
8824
8825 case value_t::number_float:
8826 {
8827 m_value = other.m_value.number_float;
8828 break;
8829 }
8830
8831 default:
Ed Tanous3dac7492017-08-02 13:46:20 -07008832 break;
Ed Tanous3dac7492017-08-02 13:46:20 -07008833 }
8834
8835 assert_invariant();
8836 }
8837
8838 /*!
8839 @brief move constructor
8840
8841 Move constructor. Constructs a JSON value with the contents of the given
8842 value @a other using move semantics. It "steals" the resources from @a
8843 other and leaves it as JSON null value.
8844
8845 @param[in,out] other value to move to this object
8846
Ed Tanousba9f9a62017-10-11 16:40:35 -07008847 @post `*this` has the same value as @a other before the call.
8848 @post @a other is a JSON null value.
Ed Tanous3dac7492017-08-02 13:46:20 -07008849
8850 @complexity Constant.
8851
Ed Tanousba9f9a62017-10-11 16:40:35 -07008852 @exceptionsafety No-throw guarantee: this constructor never throws
8853 exceptions.
8854
8855 @requirement This function helps `basic_json` satisfying the
8856 [MoveConstructible](http://en.cppreference.com/w/cpp/concept/MoveConstructible)
8857 requirements.
8858
Ed Tanous3dac7492017-08-02 13:46:20 -07008859 @liveexample{The code below shows the move constructor explicitly called
8860 via std::move.,basic_json__moveconstructor}
8861
8862 @since version 1.0.0
8863 */
8864 basic_json(basic_json&& other) noexcept
8865 : m_type(std::move(other.m_type)),
8866 m_value(std::move(other.m_value))
8867 {
8868 // check that passed value is valid
8869 other.assert_invariant();
8870
8871 // invalidate payload
8872 other.m_type = value_t::null;
8873 other.m_value = {};
8874
8875 assert_invariant();
8876 }
8877
8878 /*!
8879 @brief copy assignment
8880
8881 Copy assignment operator. Copies a JSON value via the "copy and swap"
8882 strategy: It is expressed in terms of the copy constructor, destructor,
Ed Tanousba9f9a62017-10-11 16:40:35 -07008883 and the `swap()` member function.
Ed Tanous3dac7492017-08-02 13:46:20 -07008884
8885 @param[in] other value to copy from
8886
8887 @complexity Linear.
8888
8889 @requirement This function helps `basic_json` satisfying the
8890 [Container](http://en.cppreference.com/w/cpp/concept/Container)
8891 requirements:
8892 - The complexity is linear.
8893
8894 @liveexample{The code below shows and example for the copy assignment. It
8895 creates a copy of value `a` which is then swapped with `b`. Finally\, the
8896 copy of `a` (which is the null value after the swap) is
8897 destroyed.,basic_json__copyassignment}
8898
8899 @since version 1.0.0
8900 */
8901 reference& operator=(basic_json other) noexcept (
8902 std::is_nothrow_move_constructible<value_t>::value and
8903 std::is_nothrow_move_assignable<value_t>::value and
8904 std::is_nothrow_move_constructible<json_value>::value and
8905 std::is_nothrow_move_assignable<json_value>::value
8906 )
8907 {
8908 // check that passed value is valid
8909 other.assert_invariant();
8910
8911 using std::swap;
8912 swap(m_type, other.m_type);
8913 swap(m_value, other.m_value);
8914
8915 assert_invariant();
8916 return *this;
8917 }
8918
8919 /*!
8920 @brief destructor
8921
8922 Destroys the JSON value and frees all allocated memory.
8923
8924 @complexity Linear.
8925
8926 @requirement This function helps `basic_json` satisfying the
8927 [Container](http://en.cppreference.com/w/cpp/concept/Container)
8928 requirements:
8929 - The complexity is linear.
8930 - All stored elements are destroyed and all memory is freed.
8931
8932 @since version 1.0.0
8933 */
8934 ~basic_json()
8935 {
8936 assert_invariant();
Ed Tanousba9f9a62017-10-11 16:40:35 -07008937 m_value.destroy(m_type);
Ed Tanous3dac7492017-08-02 13:46:20 -07008938 }
8939
8940 /// @}
8941
8942 public:
8943 ///////////////////////
8944 // object inspection //
8945 ///////////////////////
8946
8947 /// @name object inspection
8948 /// Functions to inspect the type of a JSON value.
8949 /// @{
8950
8951 /*!
8952 @brief serialization
8953
8954 Serialization function for JSON values. The function tries to mimic
8955 Python's `json.dumps()` function, and currently supports its @a indent
Ed Tanousba9f9a62017-10-11 16:40:35 -07008956 and @a ensure_ascii parameters.
Ed Tanous3dac7492017-08-02 13:46:20 -07008957
8958 @param[in] indent If indent is nonnegative, then array elements and object
8959 members will be pretty-printed with that indent level. An indent level of
8960 `0` will only insert newlines. `-1` (the default) selects the most compact
8961 representation.
Ed Tanousba9f9a62017-10-11 16:40:35 -07008962 @param[in] indent_char The character to use for indentation if @a indent is
8963 greater than `0`. The default is ` ` (space).
8964 @param[in] ensure_ascii If @a ensure_ascii is true, all non-ASCII characters
8965 in the output are escaped with \uXXXX sequences, and the result consists
8966 of ASCII characters only.
Ed Tanous3dac7492017-08-02 13:46:20 -07008967
8968 @return string containing the serialization of the JSON value
8969
8970 @complexity Linear.
8971
Ed Tanousba9f9a62017-10-11 16:40:35 -07008972 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
8973 changes in the JSON value.
8974
8975 @liveexample{The following example shows the effect of different @a indent\,
8976 @a indent_char\, and @a ensure_ascii parameters to the result of the
8977 serialization.,dump}
Ed Tanous3dac7492017-08-02 13:46:20 -07008978
8979 @see https://docs.python.org/2/library/json.html#json.dump
8980
Ed Tanousba9f9a62017-10-11 16:40:35 -07008981 @since version 1.0.0; indentation character @a indent_char and option
8982 @a ensure_ascii added in version 3.0.0
Ed Tanous3dac7492017-08-02 13:46:20 -07008983 */
Ed Tanousba9f9a62017-10-11 16:40:35 -07008984 string_t dump(const int indent = -1, const char indent_char = ' ',
8985 const bool ensure_ascii = false) const
Ed Tanous3dac7492017-08-02 13:46:20 -07008986 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07008987 string_t result;
8988 serializer s(detail::output_adapter<char>(result), indent_char);
Ed Tanous3dac7492017-08-02 13:46:20 -07008989
8990 if (indent >= 0)
8991 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07008992 s.dump(*this, true, ensure_ascii, static_cast<unsigned int>(indent));
Ed Tanous3dac7492017-08-02 13:46:20 -07008993 }
8994 else
8995 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07008996 s.dump(*this, false, ensure_ascii, 0);
Ed Tanous3dac7492017-08-02 13:46:20 -07008997 }
8998
Ed Tanousba9f9a62017-10-11 16:40:35 -07008999 return result;
Ed Tanous3dac7492017-08-02 13:46:20 -07009000 }
9001
9002 /*!
9003 @brief return the type of the JSON value (explicit)
9004
9005 Return the type of the JSON value as a value from the @ref value_t
9006 enumeration.
9007
9008 @return the type of the JSON value
Ed Tanousba9f9a62017-10-11 16:40:35 -07009009 Value type | return value
9010 ------------------------- | -------------------------
9011 null | value_t::null
9012 boolean | value_t::boolean
9013 string | value_t::string
9014 number (integer) | value_t::number_integer
9015 number (unsigned integer) | value_t::number_unsigned
9016 number (foating-point) | value_t::number_float
9017 object | value_t::object
9018 array | value_t::array
9019 discarded | value_t::discarded
Ed Tanous3dac7492017-08-02 13:46:20 -07009020
9021 @complexity Constant.
9022
9023 @exceptionsafety No-throw guarantee: this member function never throws
9024 exceptions.
9025
9026 @liveexample{The following code exemplifies `type()` for all JSON
9027 types.,type}
9028
Ed Tanousba9f9a62017-10-11 16:40:35 -07009029 @sa @ref operator value_t() -- return the type of the JSON value (implicit)
9030 @sa @ref type_name() -- return the type as string
9031
Ed Tanous3dac7492017-08-02 13:46:20 -07009032 @since version 1.0.0
9033 */
9034 constexpr value_t type() const noexcept
9035 {
9036 return m_type;
9037 }
9038
9039 /*!
9040 @brief return whether type is primitive
9041
Ed Tanousba9f9a62017-10-11 16:40:35 -07009042 This function returns true if and only if the JSON type is primitive
9043 (string, number, boolean, or null).
Ed Tanous3dac7492017-08-02 13:46:20 -07009044
9045 @return `true` if type is primitive (string, number, boolean, or null),
9046 `false` otherwise.
9047
9048 @complexity Constant.
9049
9050 @exceptionsafety No-throw guarantee: this member function never throws
9051 exceptions.
9052
9053 @liveexample{The following code exemplifies `is_primitive()` for all JSON
9054 types.,is_primitive}
9055
9056 @sa @ref is_structured() -- returns whether JSON value is structured
9057 @sa @ref is_null() -- returns whether JSON value is `null`
9058 @sa @ref is_string() -- returns whether JSON value is a string
9059 @sa @ref is_boolean() -- returns whether JSON value is a boolean
9060 @sa @ref is_number() -- returns whether JSON value is a number
9061
9062 @since version 1.0.0
9063 */
9064 constexpr bool is_primitive() const noexcept
9065 {
9066 return is_null() or is_string() or is_boolean() or is_number();
9067 }
9068
9069 /*!
9070 @brief return whether type is structured
9071
Ed Tanousba9f9a62017-10-11 16:40:35 -07009072 This function returns true if and only if the JSON type is structured
9073 (array or object).
Ed Tanous3dac7492017-08-02 13:46:20 -07009074
9075 @return `true` if type is structured (array or object), `false` otherwise.
9076
9077 @complexity Constant.
9078
9079 @exceptionsafety No-throw guarantee: this member function never throws
9080 exceptions.
9081
9082 @liveexample{The following code exemplifies `is_structured()` for all JSON
9083 types.,is_structured}
9084
9085 @sa @ref is_primitive() -- returns whether value is primitive
9086 @sa @ref is_array() -- returns whether value is an array
9087 @sa @ref is_object() -- returns whether value is an object
9088
9089 @since version 1.0.0
9090 */
9091 constexpr bool is_structured() const noexcept
9092 {
9093 return is_array() or is_object();
9094 }
9095
9096 /*!
9097 @brief return whether value is null
9098
Ed Tanousba9f9a62017-10-11 16:40:35 -07009099 This function returns true if and only if the JSON value is null.
Ed Tanous3dac7492017-08-02 13:46:20 -07009100
9101 @return `true` if type is null, `false` otherwise.
9102
9103 @complexity Constant.
9104
9105 @exceptionsafety No-throw guarantee: this member function never throws
9106 exceptions.
9107
9108 @liveexample{The following code exemplifies `is_null()` for all JSON
9109 types.,is_null}
9110
9111 @since version 1.0.0
9112 */
9113 constexpr bool is_null() const noexcept
9114 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07009115 return (m_type == value_t::null);
Ed Tanous3dac7492017-08-02 13:46:20 -07009116 }
9117
9118 /*!
9119 @brief return whether value is a boolean
9120
Ed Tanousba9f9a62017-10-11 16:40:35 -07009121 This function returns true if and only if the JSON value is a boolean.
Ed Tanous3dac7492017-08-02 13:46:20 -07009122
9123 @return `true` if type is boolean, `false` otherwise.
9124
9125 @complexity Constant.
9126
9127 @exceptionsafety No-throw guarantee: this member function never throws
9128 exceptions.
9129
9130 @liveexample{The following code exemplifies `is_boolean()` for all JSON
9131 types.,is_boolean}
9132
9133 @since version 1.0.0
9134 */
9135 constexpr bool is_boolean() const noexcept
9136 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07009137 return (m_type == value_t::boolean);
Ed Tanous3dac7492017-08-02 13:46:20 -07009138 }
9139
9140 /*!
9141 @brief return whether value is a number
9142
Ed Tanousba9f9a62017-10-11 16:40:35 -07009143 This function returns true if and only if the JSON value is a number. This
9144 includes both integer (signed and unsigned) and floating-point values.
Ed Tanous3dac7492017-08-02 13:46:20 -07009145
9146 @return `true` if type is number (regardless whether integer, unsigned
9147 integer or floating-type), `false` otherwise.
9148
9149 @complexity Constant.
9150
9151 @exceptionsafety No-throw guarantee: this member function never throws
9152 exceptions.
9153
9154 @liveexample{The following code exemplifies `is_number()` for all JSON
9155 types.,is_number}
9156
9157 @sa @ref is_number_integer() -- check if value is an integer or unsigned
9158 integer number
9159 @sa @ref is_number_unsigned() -- check if value is an unsigned integer
9160 number
9161 @sa @ref is_number_float() -- check if value is a floating-point number
9162
9163 @since version 1.0.0
9164 */
9165 constexpr bool is_number() const noexcept
9166 {
9167 return is_number_integer() or is_number_float();
9168 }
9169
9170 /*!
9171 @brief return whether value is an integer number
9172
Ed Tanousba9f9a62017-10-11 16:40:35 -07009173 This function returns true if and only if the JSON value is a signed or
9174 unsigned integer number. This excludes floating-point values.
Ed Tanous3dac7492017-08-02 13:46:20 -07009175
9176 @return `true` if type is an integer or unsigned integer number, `false`
9177 otherwise.
9178
9179 @complexity Constant.
9180
9181 @exceptionsafety No-throw guarantee: this member function never throws
9182 exceptions.
9183
9184 @liveexample{The following code exemplifies `is_number_integer()` for all
9185 JSON types.,is_number_integer}
9186
9187 @sa @ref is_number() -- check if value is a number
9188 @sa @ref is_number_unsigned() -- check if value is an unsigned integer
9189 number
9190 @sa @ref is_number_float() -- check if value is a floating-point number
9191
9192 @since version 1.0.0
9193 */
9194 constexpr bool is_number_integer() const noexcept
9195 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07009196 return (m_type == value_t::number_integer or m_type == value_t::number_unsigned);
Ed Tanous3dac7492017-08-02 13:46:20 -07009197 }
9198
9199 /*!
9200 @brief return whether value is an unsigned integer number
9201
Ed Tanousba9f9a62017-10-11 16:40:35 -07009202 This function returns true if and only if the JSON value is an unsigned
9203 integer number. This excludes floating-point and signed integer values.
Ed Tanous3dac7492017-08-02 13:46:20 -07009204
9205 @return `true` if type is an unsigned integer number, `false` otherwise.
9206
9207 @complexity Constant.
9208
9209 @exceptionsafety No-throw guarantee: this member function never throws
9210 exceptions.
9211
9212 @liveexample{The following code exemplifies `is_number_unsigned()` for all
9213 JSON types.,is_number_unsigned}
9214
9215 @sa @ref is_number() -- check if value is a number
9216 @sa @ref is_number_integer() -- check if value is an integer or unsigned
9217 integer number
9218 @sa @ref is_number_float() -- check if value is a floating-point number
9219
9220 @since version 2.0.0
9221 */
9222 constexpr bool is_number_unsigned() const noexcept
9223 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07009224 return (m_type == value_t::number_unsigned);
Ed Tanous3dac7492017-08-02 13:46:20 -07009225 }
9226
9227 /*!
9228 @brief return whether value is a floating-point number
9229
Ed Tanousba9f9a62017-10-11 16:40:35 -07009230 This function returns true if and only if the JSON value is a
9231 floating-point number. This excludes signed and unsigned integer values.
Ed Tanous3dac7492017-08-02 13:46:20 -07009232
9233 @return `true` if type is a floating-point number, `false` otherwise.
9234
9235 @complexity Constant.
9236
9237 @exceptionsafety No-throw guarantee: this member function never throws
9238 exceptions.
9239
9240 @liveexample{The following code exemplifies `is_number_float()` for all
9241 JSON types.,is_number_float}
9242
9243 @sa @ref is_number() -- check if value is number
9244 @sa @ref is_number_integer() -- check if value is an integer number
9245 @sa @ref is_number_unsigned() -- check if value is an unsigned integer
9246 number
9247
9248 @since version 1.0.0
9249 */
9250 constexpr bool is_number_float() const noexcept
9251 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07009252 return (m_type == value_t::number_float);
Ed Tanous3dac7492017-08-02 13:46:20 -07009253 }
9254
9255 /*!
9256 @brief return whether value is an object
9257
Ed Tanousba9f9a62017-10-11 16:40:35 -07009258 This function returns true if and only if the JSON value is an object.
Ed Tanous3dac7492017-08-02 13:46:20 -07009259
9260 @return `true` if type is object, `false` otherwise.
9261
9262 @complexity Constant.
9263
9264 @exceptionsafety No-throw guarantee: this member function never throws
9265 exceptions.
9266
9267 @liveexample{The following code exemplifies `is_object()` for all JSON
9268 types.,is_object}
9269
9270 @since version 1.0.0
9271 */
9272 constexpr bool is_object() const noexcept
9273 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07009274 return (m_type == value_t::object);
Ed Tanous3dac7492017-08-02 13:46:20 -07009275 }
9276
9277 /*!
9278 @brief return whether value is an array
9279
Ed Tanousba9f9a62017-10-11 16:40:35 -07009280 This function returns true if and only if the JSON value is an array.
Ed Tanous3dac7492017-08-02 13:46:20 -07009281
9282 @return `true` if type is array, `false` otherwise.
9283
9284 @complexity Constant.
9285
9286 @exceptionsafety No-throw guarantee: this member function never throws
9287 exceptions.
9288
9289 @liveexample{The following code exemplifies `is_array()` for all JSON
9290 types.,is_array}
9291
9292 @since version 1.0.0
9293 */
9294 constexpr bool is_array() const noexcept
9295 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07009296 return (m_type == value_t::array);
Ed Tanous3dac7492017-08-02 13:46:20 -07009297 }
9298
9299 /*!
9300 @brief return whether value is a string
9301
Ed Tanousba9f9a62017-10-11 16:40:35 -07009302 This function returns true if and only if the JSON value is a string.
Ed Tanous3dac7492017-08-02 13:46:20 -07009303
9304 @return `true` if type is string, `false` otherwise.
9305
9306 @complexity Constant.
9307
9308 @exceptionsafety No-throw guarantee: this member function never throws
9309 exceptions.
9310
9311 @liveexample{The following code exemplifies `is_string()` for all JSON
9312 types.,is_string}
9313
9314 @since version 1.0.0
9315 */
9316 constexpr bool is_string() const noexcept
9317 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07009318 return (m_type == value_t::string);
Ed Tanous3dac7492017-08-02 13:46:20 -07009319 }
9320
9321 /*!
9322 @brief return whether value is discarded
9323
Ed Tanousba9f9a62017-10-11 16:40:35 -07009324 This function returns true if and only if the JSON value was discarded
9325 during parsing with a callback function (see @ref parser_callback_t).
Ed Tanous3dac7492017-08-02 13:46:20 -07009326
9327 @note This function will always be `false` for JSON values after parsing.
9328 That is, discarded values can only occur during parsing, but will be
9329 removed when inside a structured value or replaced by null in other cases.
9330
9331 @return `true` if type is discarded, `false` otherwise.
9332
9333 @complexity Constant.
9334
9335 @exceptionsafety No-throw guarantee: this member function never throws
9336 exceptions.
9337
9338 @liveexample{The following code exemplifies `is_discarded()` for all JSON
9339 types.,is_discarded}
9340
9341 @since version 1.0.0
9342 */
9343 constexpr bool is_discarded() const noexcept
9344 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07009345 return (m_type == value_t::discarded);
Ed Tanous3dac7492017-08-02 13:46:20 -07009346 }
9347
9348 /*!
9349 @brief return the type of the JSON value (implicit)
9350
9351 Implicitly return the type of the JSON value as a value from the @ref
9352 value_t enumeration.
9353
9354 @return the type of the JSON value
9355
9356 @complexity Constant.
9357
9358 @exceptionsafety No-throw guarantee: this member function never throws
9359 exceptions.
9360
9361 @liveexample{The following code exemplifies the @ref value_t operator for
9362 all JSON types.,operator__value_t}
9363
Ed Tanousba9f9a62017-10-11 16:40:35 -07009364 @sa @ref type() -- return the type of the JSON value (explicit)
9365 @sa @ref type_name() -- return the type as string
9366
Ed Tanous3dac7492017-08-02 13:46:20 -07009367 @since version 1.0.0
9368 */
9369 constexpr operator value_t() const noexcept
9370 {
9371 return m_type;
9372 }
9373
9374 /// @}
9375
9376 private:
9377 //////////////////
9378 // value access //
9379 //////////////////
9380
9381 /// get a boolean (explicit)
9382 boolean_t get_impl(boolean_t* /*unused*/) const
9383 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07009384 if (JSON_LIKELY(is_boolean()))
Ed Tanous3dac7492017-08-02 13:46:20 -07009385 {
9386 return m_value.boolean;
9387 }
9388
Ed Tanousba9f9a62017-10-11 16:40:35 -07009389 JSON_THROW(type_error::create(302, "type must be boolean, but is " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07009390 }
9391
9392 /// get a pointer to the value (object)
9393 object_t* get_impl_ptr(object_t* /*unused*/) noexcept
9394 {
9395 return is_object() ? m_value.object : nullptr;
9396 }
9397
9398 /// get a pointer to the value (object)
9399 constexpr const object_t* get_impl_ptr(const object_t* /*unused*/) const noexcept
9400 {
9401 return is_object() ? m_value.object : nullptr;
9402 }
9403
9404 /// get a pointer to the value (array)
9405 array_t* get_impl_ptr(array_t* /*unused*/) noexcept
9406 {
9407 return is_array() ? m_value.array : nullptr;
9408 }
9409
9410 /// get a pointer to the value (array)
9411 constexpr const array_t* get_impl_ptr(const array_t* /*unused*/) const noexcept
9412 {
9413 return is_array() ? m_value.array : nullptr;
9414 }
9415
9416 /// get a pointer to the value (string)
9417 string_t* get_impl_ptr(string_t* /*unused*/) noexcept
9418 {
9419 return is_string() ? m_value.string : nullptr;
9420 }
9421
9422 /// get a pointer to the value (string)
9423 constexpr const string_t* get_impl_ptr(const string_t* /*unused*/) const noexcept
9424 {
9425 return is_string() ? m_value.string : nullptr;
9426 }
9427
9428 /// get a pointer to the value (boolean)
9429 boolean_t* get_impl_ptr(boolean_t* /*unused*/) noexcept
9430 {
9431 return is_boolean() ? &m_value.boolean : nullptr;
9432 }
9433
9434 /// get a pointer to the value (boolean)
9435 constexpr const boolean_t* get_impl_ptr(const boolean_t* /*unused*/) const noexcept
9436 {
9437 return is_boolean() ? &m_value.boolean : nullptr;
9438 }
9439
9440 /// get a pointer to the value (integer number)
9441 number_integer_t* get_impl_ptr(number_integer_t* /*unused*/) noexcept
9442 {
9443 return is_number_integer() ? &m_value.number_integer : nullptr;
9444 }
9445
9446 /// get a pointer to the value (integer number)
9447 constexpr const number_integer_t* get_impl_ptr(const number_integer_t* /*unused*/) const noexcept
9448 {
9449 return is_number_integer() ? &m_value.number_integer : nullptr;
9450 }
9451
9452 /// get a pointer to the value (unsigned number)
9453 number_unsigned_t* get_impl_ptr(number_unsigned_t* /*unused*/) noexcept
9454 {
9455 return is_number_unsigned() ? &m_value.number_unsigned : nullptr;
9456 }
9457
9458 /// get a pointer to the value (unsigned number)
9459 constexpr const number_unsigned_t* get_impl_ptr(const number_unsigned_t* /*unused*/) const noexcept
9460 {
9461 return is_number_unsigned() ? &m_value.number_unsigned : nullptr;
9462 }
9463
9464 /// get a pointer to the value (floating-point number)
9465 number_float_t* get_impl_ptr(number_float_t* /*unused*/) noexcept
9466 {
9467 return is_number_float() ? &m_value.number_float : nullptr;
9468 }
9469
9470 /// get a pointer to the value (floating-point number)
9471 constexpr const number_float_t* get_impl_ptr(const number_float_t* /*unused*/) const noexcept
9472 {
9473 return is_number_float() ? &m_value.number_float : nullptr;
9474 }
9475
9476 /*!
9477 @brief helper function to implement get_ref()
9478
Ed Tanousba9f9a62017-10-11 16:40:35 -07009479 This function helps to implement get_ref() without code duplication for
Ed Tanous3dac7492017-08-02 13:46:20 -07009480 const and non-const overloads
9481
9482 @tparam ThisType will be deduced as `basic_json` or `const basic_json`
9483
Ed Tanousba9f9a62017-10-11 16:40:35 -07009484 @throw type_error.303 if ReferenceType does not match underlying value
Ed Tanous3dac7492017-08-02 13:46:20 -07009485 type of the current JSON
9486 */
9487 template<typename ReferenceType, typename ThisType>
9488 static ReferenceType get_ref_impl(ThisType& obj)
9489 {
Ed Tanous3dac7492017-08-02 13:46:20 -07009490 // delegate the call to get_ptr<>()
Ed Tanousba9f9a62017-10-11 16:40:35 -07009491 auto ptr = obj.template get_ptr<typename std::add_pointer<ReferenceType>::type>();
Ed Tanous3dac7492017-08-02 13:46:20 -07009492
Ed Tanousba9f9a62017-10-11 16:40:35 -07009493 if (JSON_LIKELY(ptr != nullptr))
Ed Tanous3dac7492017-08-02 13:46:20 -07009494 {
9495 return *ptr;
9496 }
9497
Ed Tanousba9f9a62017-10-11 16:40:35 -07009498 JSON_THROW(type_error::create(303, "incompatible ReferenceType for get_ref, actual type is " + std::string(obj.type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07009499 }
9500
9501 public:
9502 /// @name value access
9503 /// Direct access to the stored value of a JSON value.
9504 /// @{
9505
9506 /*!
9507 @brief get special-case overload
9508
9509 This overloads avoids a lot of template boilerplate, it can be seen as the
9510 identity method
9511
9512 @tparam BasicJsonType == @ref basic_json
9513
9514 @return a copy of *this
9515
9516 @complexity Constant.
9517
9518 @since version 2.1.0
9519 */
9520 template <
9521 typename BasicJsonType,
9522 detail::enable_if_t<std::is_same<typename std::remove_const<BasicJsonType>::type,
9523 basic_json_t>::value,
9524 int> = 0 >
9525 basic_json get() const
9526 {
9527 return *this;
9528 }
9529
9530 /*!
9531 @brief get a value (explicit)
9532
9533 Explicit type conversion between the JSON value and a compatible value
9534 which is [CopyConstructible](http://en.cppreference.com/w/cpp/concept/CopyConstructible)
9535 and [DefaultConstructible](http://en.cppreference.com/w/cpp/concept/DefaultConstructible).
9536 The value is converted by calling the @ref json_serializer<ValueType>
9537 `from_json()` method.
9538
9539 The function is equivalent to executing
9540 @code {.cpp}
9541 ValueType ret;
9542 JSONSerializer<ValueType>::from_json(*this, ret);
9543 return ret;
9544 @endcode
9545
9546 This overloads is chosen if:
9547 - @a ValueType is not @ref basic_json,
9548 - @ref json_serializer<ValueType> has a `from_json()` method of the form
Ed Tanousba9f9a62017-10-11 16:40:35 -07009549 `void from_json(const basic_json&, ValueType&)`, and
Ed Tanous3dac7492017-08-02 13:46:20 -07009550 - @ref json_serializer<ValueType> does not have a `from_json()` method of
Ed Tanousba9f9a62017-10-11 16:40:35 -07009551 the form `ValueType from_json(const basic_json&)`
Ed Tanous3dac7492017-08-02 13:46:20 -07009552
9553 @tparam ValueTypeCV the provided value type
9554 @tparam ValueType the returned value type
9555
9556 @return copy of the JSON value, converted to @a ValueType
9557
9558 @throw what @ref json_serializer<ValueType> `from_json()` method throws
9559
9560 @liveexample{The example below shows several conversions from JSON values
9561 to other types. There a few things to note: (1) Floating-point numbers can
9562 be converted to integers\, (2) A JSON array can be converted to a standard
9563 `std::vector<short>`\, (3) A JSON object can be converted to C++
9564 associative containers such as `std::unordered_map<std::string\,
9565 json>`.,get__ValueType_const}
9566
9567 @since version 2.1.0
9568 */
9569 template <
9570 typename ValueTypeCV,
9571 typename ValueType = detail::uncvref_t<ValueTypeCV>,
9572 detail::enable_if_t <
9573 not std::is_same<basic_json_t, ValueType>::value and
9574 detail::has_from_json<basic_json_t, ValueType>::value and
9575 not detail::has_non_default_from_json<basic_json_t, ValueType>::value,
9576 int > = 0 >
9577 ValueType get() const noexcept(noexcept(
9578 JSONSerializer<ValueType>::from_json(std::declval<const basic_json_t&>(), std::declval<ValueType&>())))
9579 {
9580 // we cannot static_assert on ValueTypeCV being non-const, because
9581 // there is support for get<const basic_json_t>(), which is why we
9582 // still need the uncvref
9583 static_assert(not std::is_reference<ValueTypeCV>::value,
9584 "get() cannot be used with reference types, you might want to use get_ref()");
9585 static_assert(std::is_default_constructible<ValueType>::value,
9586 "types must be DefaultConstructible when used with get()");
9587
9588 ValueType ret;
9589 JSONSerializer<ValueType>::from_json(*this, ret);
9590 return ret;
9591 }
9592
9593 /*!
9594 @brief get a value (explicit); special case
9595
9596 Explicit type conversion between the JSON value and a compatible value
9597 which is **not** [CopyConstructible](http://en.cppreference.com/w/cpp/concept/CopyConstructible)
9598 and **not** [DefaultConstructible](http://en.cppreference.com/w/cpp/concept/DefaultConstructible).
9599 The value is converted by calling the @ref json_serializer<ValueType>
9600 `from_json()` method.
9601
9602 The function is equivalent to executing
9603 @code {.cpp}
9604 return JSONSerializer<ValueTypeCV>::from_json(*this);
9605 @endcode
9606
9607 This overloads is chosen if:
9608 - @a ValueType is not @ref basic_json and
9609 - @ref json_serializer<ValueType> has a `from_json()` method of the form
Ed Tanousba9f9a62017-10-11 16:40:35 -07009610 `ValueType from_json(const basic_json&)`
Ed Tanous3dac7492017-08-02 13:46:20 -07009611
9612 @note If @ref json_serializer<ValueType> has both overloads of
9613 `from_json()`, this one is chosen.
9614
9615 @tparam ValueTypeCV the provided value type
9616 @tparam ValueType the returned value type
9617
9618 @return copy of the JSON value, converted to @a ValueType
9619
9620 @throw what @ref json_serializer<ValueType> `from_json()` method throws
9621
9622 @since version 2.1.0
9623 */
9624 template <
9625 typename ValueTypeCV,
9626 typename ValueType = detail::uncvref_t<ValueTypeCV>,
9627 detail::enable_if_t<not std::is_same<basic_json_t, ValueType>::value and
9628 detail::has_non_default_from_json<basic_json_t,
9629 ValueType>::value, int> = 0 >
9630 ValueType get() const noexcept(noexcept(
9631 JSONSerializer<ValueTypeCV>::from_json(std::declval<const basic_json_t&>())))
9632 {
9633 static_assert(not std::is_reference<ValueTypeCV>::value,
9634 "get() cannot be used with reference types, you might want to use get_ref()");
9635 return JSONSerializer<ValueTypeCV>::from_json(*this);
9636 }
9637
9638 /*!
9639 @brief get a pointer value (explicit)
9640
9641 Explicit pointer access to the internally stored JSON value. No copies are
9642 made.
9643
9644 @warning The pointer becomes invalid if the underlying JSON object
9645 changes.
9646
9647 @tparam PointerType pointer type; must be a pointer to @ref array_t, @ref
9648 object_t, @ref string_t, @ref boolean_t, @ref number_integer_t,
9649 @ref number_unsigned_t, or @ref number_float_t.
9650
9651 @return pointer to the internally stored JSON value if the requested
9652 pointer type @a PointerType fits to the JSON value; `nullptr` otherwise
9653
9654 @complexity Constant.
9655
9656 @liveexample{The example below shows how pointers to internal values of a
9657 JSON value can be requested. Note that no type conversions are made and a
9658 `nullptr` is returned if the value and the requested pointer type does not
9659 match.,get__PointerType}
9660
9661 @sa @ref get_ptr() for explicit pointer-member access
9662
9663 @since version 1.0.0
9664 */
9665 template<typename PointerType, typename std::enable_if<
9666 std::is_pointer<PointerType>::value, int>::type = 0>
9667 PointerType get() noexcept
9668 {
9669 // delegate the call to get_ptr
9670 return get_ptr<PointerType>();
9671 }
9672
9673 /*!
9674 @brief get a pointer value (explicit)
9675 @copydoc get()
9676 */
9677 template<typename PointerType, typename std::enable_if<
9678 std::is_pointer<PointerType>::value, int>::type = 0>
9679 constexpr const PointerType get() const noexcept
9680 {
9681 // delegate the call to get_ptr
9682 return get_ptr<PointerType>();
9683 }
9684
9685 /*!
9686 @brief get a pointer value (implicit)
9687
9688 Implicit pointer access to the internally stored JSON value. No copies are
9689 made.
9690
9691 @warning Writing data to the pointee of the result yields an undefined
9692 state.
9693
9694 @tparam PointerType pointer type; must be a pointer to @ref array_t, @ref
9695 object_t, @ref string_t, @ref boolean_t, @ref number_integer_t,
9696 @ref number_unsigned_t, or @ref number_float_t. Enforced by a static
9697 assertion.
9698
9699 @return pointer to the internally stored JSON value if the requested
9700 pointer type @a PointerType fits to the JSON value; `nullptr` otherwise
9701
9702 @complexity Constant.
9703
9704 @liveexample{The example below shows how pointers to internal values of a
9705 JSON value can be requested. Note that no type conversions are made and a
9706 `nullptr` is returned if the value and the requested pointer type does not
9707 match.,get_ptr}
9708
9709 @since version 1.0.0
9710 */
9711 template<typename PointerType, typename std::enable_if<
9712 std::is_pointer<PointerType>::value, int>::type = 0>
9713 PointerType get_ptr() noexcept
9714 {
9715 // get the type of the PointerType (remove pointer and const)
9716 using pointee_t = typename std::remove_const<typename
9717 std::remove_pointer<typename
9718 std::remove_const<PointerType>::type>::type>::type;
9719 // make sure the type matches the allowed types
9720 static_assert(
9721 std::is_same<object_t, pointee_t>::value
9722 or std::is_same<array_t, pointee_t>::value
9723 or std::is_same<string_t, pointee_t>::value
9724 or std::is_same<boolean_t, pointee_t>::value
9725 or std::is_same<number_integer_t, pointee_t>::value
9726 or std::is_same<number_unsigned_t, pointee_t>::value
9727 or std::is_same<number_float_t, pointee_t>::value
9728 , "incompatible pointer type");
9729
9730 // delegate the call to get_impl_ptr<>()
9731 return get_impl_ptr(static_cast<PointerType>(nullptr));
9732 }
9733
9734 /*!
9735 @brief get a pointer value (implicit)
9736 @copydoc get_ptr()
9737 */
9738 template<typename PointerType, typename std::enable_if<
9739 std::is_pointer<PointerType>::value and
9740 std::is_const<typename std::remove_pointer<PointerType>::type>::value, int>::type = 0>
9741 constexpr const PointerType get_ptr() const noexcept
9742 {
9743 // get the type of the PointerType (remove pointer and const)
9744 using pointee_t = typename std::remove_const<typename
9745 std::remove_pointer<typename
9746 std::remove_const<PointerType>::type>::type>::type;
9747 // make sure the type matches the allowed types
9748 static_assert(
9749 std::is_same<object_t, pointee_t>::value
9750 or std::is_same<array_t, pointee_t>::value
9751 or std::is_same<string_t, pointee_t>::value
9752 or std::is_same<boolean_t, pointee_t>::value
9753 or std::is_same<number_integer_t, pointee_t>::value
9754 or std::is_same<number_unsigned_t, pointee_t>::value
9755 or std::is_same<number_float_t, pointee_t>::value
9756 , "incompatible pointer type");
9757
9758 // delegate the call to get_impl_ptr<>() const
Ed Tanousba9f9a62017-10-11 16:40:35 -07009759 return get_impl_ptr(static_cast<PointerType>(nullptr));
Ed Tanous3dac7492017-08-02 13:46:20 -07009760 }
9761
9762 /*!
9763 @brief get a reference value (implicit)
9764
9765 Implicit reference access to the internally stored JSON value. No copies
9766 are made.
9767
9768 @warning Writing data to the referee of the result yields an undefined
9769 state.
9770
9771 @tparam ReferenceType reference type; must be a reference to @ref array_t,
9772 @ref object_t, @ref string_t, @ref boolean_t, @ref number_integer_t, or
9773 @ref number_float_t. Enforced by static assertion.
9774
9775 @return reference to the internally stored JSON value if the requested
9776 reference type @a ReferenceType fits to the JSON value; throws
Ed Tanousba9f9a62017-10-11 16:40:35 -07009777 type_error.303 otherwise
Ed Tanous3dac7492017-08-02 13:46:20 -07009778
Ed Tanousba9f9a62017-10-11 16:40:35 -07009779 @throw type_error.303 in case passed type @a ReferenceType is incompatible
9780 with the stored JSON value; see example below
Ed Tanous3dac7492017-08-02 13:46:20 -07009781
9782 @complexity Constant.
9783
9784 @liveexample{The example shows several calls to `get_ref()`.,get_ref}
9785
9786 @since version 1.1.0
9787 */
9788 template<typename ReferenceType, typename std::enable_if<
9789 std::is_reference<ReferenceType>::value, int>::type = 0>
9790 ReferenceType get_ref()
9791 {
9792 // delegate call to get_ref_impl
9793 return get_ref_impl<ReferenceType>(*this);
9794 }
9795
9796 /*!
9797 @brief get a reference value (implicit)
9798 @copydoc get_ref()
9799 */
9800 template<typename ReferenceType, typename std::enable_if<
9801 std::is_reference<ReferenceType>::value and
9802 std::is_const<typename std::remove_reference<ReferenceType>::type>::value, int>::type = 0>
9803 ReferenceType get_ref() const
9804 {
9805 // delegate call to get_ref_impl
9806 return get_ref_impl<ReferenceType>(*this);
9807 }
9808
9809 /*!
9810 @brief get a value (implicit)
9811
9812 Implicit type conversion between the JSON value and a compatible value.
9813 The call is realized by calling @ref get() const.
9814
9815 @tparam ValueType non-pointer type compatible to the JSON value, for
9816 instance `int` for JSON integer numbers, `bool` for JSON booleans, or
9817 `std::vector` types for JSON arrays. The character type of @ref string_t
9818 as well as an initializer list of this type is excluded to avoid
9819 ambiguities as these types implicitly convert to `std::string`.
9820
9821 @return copy of the JSON value, converted to type @a ValueType
9822
Ed Tanousba9f9a62017-10-11 16:40:35 -07009823 @throw type_error.302 in case passed type @a ValueType is incompatible
9824 to the JSON value type (e.g., the JSON value is of type boolean, but a
9825 string is requested); see example below
Ed Tanous3dac7492017-08-02 13:46:20 -07009826
9827 @complexity Linear in the size of the JSON value.
9828
9829 @liveexample{The example below shows several conversions from JSON values
9830 to other types. There a few things to note: (1) Floating-point numbers can
9831 be converted to integers\, (2) A JSON array can be converted to a standard
9832 `std::vector<short>`\, (3) A JSON object can be converted to C++
9833 associative containers such as `std::unordered_map<std::string\,
9834 json>`.,operator__ValueType}
9835
9836 @since version 1.0.0
9837 */
9838 template < typename ValueType, typename std::enable_if <
9839 not std::is_pointer<ValueType>::value and
Ed Tanousba9f9a62017-10-11 16:40:35 -07009840 not std::is_same<ValueType, detail::json_ref<basic_json>>::value and
Ed Tanous3dac7492017-08-02 13:46:20 -07009841 not std::is_same<ValueType, typename string_t::value_type>::value
9842#ifndef _MSC_VER // fix for issue #167 operator<< ambiguity under VS2015
9843 and not std::is_same<ValueType, std::initializer_list<typename string_t::value_type>>::value
9844#endif
Ed Tanousba9f9a62017-10-11 16:40:35 -07009845#if (defined(__cplusplus) && __cplusplus >= 201703L) || (defined(_MSC_VER) && _MSC_VER >1900 && defined(_HAS_CXX17) && _HAS_CXX17 == 1) // fix for issue #464
9846 and not std::is_same<ValueType, typename std::string_view>::value
9847#endif
Ed Tanous3dac7492017-08-02 13:46:20 -07009848 , int >::type = 0 >
9849 operator ValueType() const
9850 {
9851 // delegate the call to get<>() const
9852 return get<ValueType>();
9853 }
9854
9855 /// @}
9856
9857
9858 ////////////////////
9859 // element access //
9860 ////////////////////
9861
9862 /// @name element access
9863 /// Access to the JSON value.
9864 /// @{
9865
9866 /*!
9867 @brief access specified array element with bounds checking
9868
9869 Returns a reference to the element at specified location @a idx, with
9870 bounds checking.
9871
9872 @param[in] idx index of the element to access
9873
9874 @return reference to the element at index @a idx
9875
Ed Tanousba9f9a62017-10-11 16:40:35 -07009876 @throw type_error.304 if the JSON value is not an array; in this case,
9877 calling `at` with an index makes no sense. See example below.
9878 @throw out_of_range.401 if the index @a idx is out of range of the array;
9879 that is, `idx >= size()`. See example below.
9880
9881 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
9882 changes in the JSON value.
Ed Tanous3dac7492017-08-02 13:46:20 -07009883
9884 @complexity Constant.
9885
Ed Tanous3dac7492017-08-02 13:46:20 -07009886 @since version 1.0.0
Ed Tanousba9f9a62017-10-11 16:40:35 -07009887
9888 @liveexample{The example below shows how array elements can be read and
9889 written using `at()`. It also demonstrates the different exceptions that
9890 can be thrown.,at__size_type}
Ed Tanous3dac7492017-08-02 13:46:20 -07009891 */
9892 reference at(size_type idx)
9893 {
9894 // at only works for arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -07009895 if (JSON_LIKELY(is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -07009896 {
9897 JSON_TRY
9898 {
9899 return m_value.array->at(idx);
9900 }
9901 JSON_CATCH (std::out_of_range&)
9902 {
9903 // create better exception explanation
Ed Tanousba9f9a62017-10-11 16:40:35 -07009904 JSON_THROW(out_of_range::create(401, "array index " + std::to_string(idx) + " is out of range"));
Ed Tanous3dac7492017-08-02 13:46:20 -07009905 }
9906 }
9907 else
9908 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07009909 JSON_THROW(type_error::create(304, "cannot use at() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07009910 }
9911 }
9912
9913 /*!
9914 @brief access specified array element with bounds checking
9915
9916 Returns a const reference to the element at specified location @a idx,
9917 with bounds checking.
9918
9919 @param[in] idx index of the element to access
9920
9921 @return const reference to the element at index @a idx
9922
Ed Tanousba9f9a62017-10-11 16:40:35 -07009923 @throw type_error.304 if the JSON value is not an array; in this case,
9924 calling `at` with an index makes no sense. See example below.
9925 @throw out_of_range.401 if the index @a idx is out of range of the array;
9926 that is, `idx >= size()`. See example below.
9927
9928 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
9929 changes in the JSON value.
Ed Tanous3dac7492017-08-02 13:46:20 -07009930
9931 @complexity Constant.
9932
Ed Tanous3dac7492017-08-02 13:46:20 -07009933 @since version 1.0.0
Ed Tanousba9f9a62017-10-11 16:40:35 -07009934
9935 @liveexample{The example below shows how array elements can be read using
9936 `at()`. It also demonstrates the different exceptions that can be thrown.,
9937 at__size_type_const}
Ed Tanous3dac7492017-08-02 13:46:20 -07009938 */
9939 const_reference at(size_type idx) const
9940 {
9941 // at only works for arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -07009942 if (JSON_LIKELY(is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -07009943 {
9944 JSON_TRY
9945 {
9946 return m_value.array->at(idx);
9947 }
9948 JSON_CATCH (std::out_of_range&)
9949 {
9950 // create better exception explanation
Ed Tanousba9f9a62017-10-11 16:40:35 -07009951 JSON_THROW(out_of_range::create(401, "array index " + std::to_string(idx) + " is out of range"));
Ed Tanous3dac7492017-08-02 13:46:20 -07009952 }
9953 }
9954 else
9955 {
Ed Tanousba9f9a62017-10-11 16:40:35 -07009956 JSON_THROW(type_error::create(304, "cannot use at() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -07009957 }
9958 }
9959
9960 /*!
9961 @brief access specified object element with bounds checking
9962
9963 Returns a reference to the element at with specified key @a key, with
9964 bounds checking.
9965
9966 @param[in] key key of the element to access
9967
9968 @return reference to the element at key @a key
9969
Ed Tanousba9f9a62017-10-11 16:40:35 -07009970 @throw type_error.304 if the JSON value is not an object; in this case,
9971 calling `at` with a key makes no sense. See example below.
9972 @throw out_of_range.403 if the key @a key is is not stored in the object;
9973 that is, `find(key) == end()`. See example below.
9974
9975 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
9976 changes in the JSON value.
Ed Tanous3dac7492017-08-02 13:46:20 -07009977
9978 @complexity Logarithmic in the size of the container.
9979
Ed Tanous3dac7492017-08-02 13:46:20 -07009980 @sa @ref operator[](const typename object_t::key_type&) for unchecked
9981 access by reference
9982 @sa @ref value() for access by value with a default value
9983
9984 @since version 1.0.0
Ed Tanousba9f9a62017-10-11 16:40:35 -07009985
9986 @liveexample{The example below shows how object elements can be read and
9987 written using `at()`. It also demonstrates the different exceptions that
9988 can be thrown.,at__object_t_key_type}
Ed Tanous3dac7492017-08-02 13:46:20 -07009989 */
9990 reference at(const typename object_t::key_type& key)
9991 {
9992 // at only works for objects
Ed Tanousba9f9a62017-10-11 16:40:35 -07009993 if (JSON_LIKELY(is_object()))
Ed Tanous3dac7492017-08-02 13:46:20 -07009994 {
9995 JSON_TRY
9996 {
9997 return m_value.object->at(key);
9998 }
9999 JSON_CATCH (std::out_of_range&)
10000 {
10001 // create better exception explanation
Ed Tanousba9f9a62017-10-11 16:40:35 -070010002 JSON_THROW(out_of_range::create(403, "key '" + key + "' not found"));
Ed Tanous3dac7492017-08-02 13:46:20 -070010003 }
10004 }
10005 else
10006 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070010007 JSON_THROW(type_error::create(304, "cannot use at() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010008 }
10009 }
10010
10011 /*!
10012 @brief access specified object element with bounds checking
10013
10014 Returns a const reference to the element at with specified key @a key,
10015 with bounds checking.
10016
10017 @param[in] key key of the element to access
10018
10019 @return const reference to the element at key @a key
10020
Ed Tanousba9f9a62017-10-11 16:40:35 -070010021 @throw type_error.304 if the JSON value is not an object; in this case,
10022 calling `at` with a key makes no sense. See example below.
10023 @throw out_of_range.403 if the key @a key is is not stored in the object;
10024 that is, `find(key) == end()`. See example below.
10025
10026 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
10027 changes in the JSON value.
Ed Tanous3dac7492017-08-02 13:46:20 -070010028
10029 @complexity Logarithmic in the size of the container.
10030
Ed Tanous3dac7492017-08-02 13:46:20 -070010031 @sa @ref operator[](const typename object_t::key_type&) for unchecked
10032 access by reference
10033 @sa @ref value() for access by value with a default value
10034
10035 @since version 1.0.0
Ed Tanousba9f9a62017-10-11 16:40:35 -070010036
10037 @liveexample{The example below shows how object elements can be read using
10038 `at()`. It also demonstrates the different exceptions that can be thrown.,
10039 at__object_t_key_type_const}
Ed Tanous3dac7492017-08-02 13:46:20 -070010040 */
10041 const_reference at(const typename object_t::key_type& key) const
10042 {
10043 // at only works for objects
Ed Tanousba9f9a62017-10-11 16:40:35 -070010044 if (JSON_LIKELY(is_object()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010045 {
10046 JSON_TRY
10047 {
10048 return m_value.object->at(key);
10049 }
10050 JSON_CATCH (std::out_of_range&)
10051 {
10052 // create better exception explanation
Ed Tanousba9f9a62017-10-11 16:40:35 -070010053 JSON_THROW(out_of_range::create(403, "key '" + key + "' not found"));
Ed Tanous3dac7492017-08-02 13:46:20 -070010054 }
10055 }
10056 else
10057 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070010058 JSON_THROW(type_error::create(304, "cannot use at() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010059 }
10060 }
10061
10062 /*!
10063 @brief access specified array element
10064
10065 Returns a reference to the element at specified location @a idx.
10066
10067 @note If @a idx is beyond the range of the array (i.e., `idx >= size()`),
10068 then the array is silently filled up with `null` values to make `idx` a
10069 valid reference to the last stored element.
10070
10071 @param[in] idx index of the element to access
10072
10073 @return reference to the element at index @a idx
10074
Ed Tanousba9f9a62017-10-11 16:40:35 -070010075 @throw type_error.305 if the JSON value is not an array or null; in that
10076 cases, using the [] operator with an index makes no sense.
Ed Tanous3dac7492017-08-02 13:46:20 -070010077
10078 @complexity Constant if @a idx is in the range of the array. Otherwise
10079 linear in `idx - size()`.
10080
10081 @liveexample{The example below shows how array elements can be read and
10082 written using `[]` operator. Note the addition of `null`
10083 values.,operatorarray__size_type}
10084
10085 @since version 1.0.0
10086 */
10087 reference operator[](size_type idx)
10088 {
10089 // implicitly convert null value to an empty array
10090 if (is_null())
10091 {
10092 m_type = value_t::array;
10093 m_value.array = create<array_t>();
10094 assert_invariant();
10095 }
10096
10097 // operator[] only works for arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -070010098 if (JSON_LIKELY(is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010099 {
10100 // fill up array with null values if given idx is outside range
10101 if (idx >= m_value.array->size())
10102 {
10103 m_value.array->insert(m_value.array->end(),
10104 idx - m_value.array->size() + 1,
10105 basic_json());
10106 }
10107
10108 return m_value.array->operator[](idx);
10109 }
10110
Ed Tanousba9f9a62017-10-11 16:40:35 -070010111 JSON_THROW(type_error::create(305, "cannot use operator[] with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010112 }
10113
10114 /*!
10115 @brief access specified array element
10116
10117 Returns a const reference to the element at specified location @a idx.
10118
10119 @param[in] idx index of the element to access
10120
10121 @return const reference to the element at index @a idx
10122
Ed Tanousba9f9a62017-10-11 16:40:35 -070010123 @throw type_error.305 if the JSON value is not an array; in that cases,
10124 using the [] operator with an index makes no sense.
Ed Tanous3dac7492017-08-02 13:46:20 -070010125
10126 @complexity Constant.
10127
10128 @liveexample{The example below shows how array elements can be read using
10129 the `[]` operator.,operatorarray__size_type_const}
10130
10131 @since version 1.0.0
10132 */
10133 const_reference operator[](size_type idx) const
10134 {
10135 // const operator[] only works for arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -070010136 if (JSON_LIKELY(is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010137 {
10138 return m_value.array->operator[](idx);
10139 }
10140
Ed Tanousba9f9a62017-10-11 16:40:35 -070010141 JSON_THROW(type_error::create(305, "cannot use operator[] with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010142 }
10143
10144 /*!
10145 @brief access specified object element
10146
10147 Returns a reference to the element at with specified key @a key.
10148
10149 @note If @a key is not found in the object, then it is silently added to
10150 the object and filled with a `null` value to make `key` a valid reference.
10151 In case the value was `null` before, it is converted to an object.
10152
10153 @param[in] key key of the element to access
10154
10155 @return reference to the element at key @a key
10156
Ed Tanousba9f9a62017-10-11 16:40:35 -070010157 @throw type_error.305 if the JSON value is not an object or null; in that
10158 cases, using the [] operator with a key makes no sense.
Ed Tanous3dac7492017-08-02 13:46:20 -070010159
10160 @complexity Logarithmic in the size of the container.
10161
10162 @liveexample{The example below shows how object elements can be read and
10163 written using the `[]` operator.,operatorarray__key_type}
10164
10165 @sa @ref at(const typename object_t::key_type&) for access by reference
10166 with range checking
10167 @sa @ref value() for access by value with a default value
10168
10169 @since version 1.0.0
10170 */
10171 reference operator[](const typename object_t::key_type& key)
10172 {
10173 // implicitly convert null value to an empty object
10174 if (is_null())
10175 {
10176 m_type = value_t::object;
10177 m_value.object = create<object_t>();
10178 assert_invariant();
10179 }
10180
10181 // operator[] only works for objects
Ed Tanousba9f9a62017-10-11 16:40:35 -070010182 if (JSON_LIKELY(is_object()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010183 {
10184 return m_value.object->operator[](key);
10185 }
10186
Ed Tanousba9f9a62017-10-11 16:40:35 -070010187 JSON_THROW(type_error::create(305, "cannot use operator[] with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010188 }
10189
10190 /*!
10191 @brief read-only access specified object element
10192
10193 Returns a const reference to the element at with specified key @a key. No
10194 bounds checking is performed.
10195
10196 @warning If the element with key @a key does not exist, the behavior is
10197 undefined.
10198
10199 @param[in] key key of the element to access
10200
10201 @return const reference to the element at key @a key
10202
10203 @pre The element with key @a key must exist. **This precondition is
10204 enforced with an assertion.**
10205
Ed Tanousba9f9a62017-10-11 16:40:35 -070010206 @throw type_error.305 if the JSON value is not an object; in that cases,
10207 using the [] operator with a key makes no sense.
Ed Tanous3dac7492017-08-02 13:46:20 -070010208
10209 @complexity Logarithmic in the size of the container.
10210
10211 @liveexample{The example below shows how object elements can be read using
10212 the `[]` operator.,operatorarray__key_type_const}
10213
10214 @sa @ref at(const typename object_t::key_type&) for access by reference
10215 with range checking
10216 @sa @ref value() for access by value with a default value
10217
10218 @since version 1.0.0
10219 */
10220 const_reference operator[](const typename object_t::key_type& key) const
10221 {
10222 // const operator[] only works for objects
Ed Tanousba9f9a62017-10-11 16:40:35 -070010223 if (JSON_LIKELY(is_object()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010224 {
10225 assert(m_value.object->find(key) != m_value.object->end());
10226 return m_value.object->find(key)->second;
10227 }
10228
Ed Tanousba9f9a62017-10-11 16:40:35 -070010229 JSON_THROW(type_error::create(305, "cannot use operator[] with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010230 }
10231
10232 /*!
10233 @brief access specified object element
10234
10235 Returns a reference to the element at with specified key @a key.
10236
10237 @note If @a key is not found in the object, then it is silently added to
10238 the object and filled with a `null` value to make `key` a valid reference.
10239 In case the value was `null` before, it is converted to an object.
10240
10241 @param[in] key key of the element to access
10242
10243 @return reference to the element at key @a key
10244
Ed Tanousba9f9a62017-10-11 16:40:35 -070010245 @throw type_error.305 if the JSON value is not an object or null; in that
10246 cases, using the [] operator with a key makes no sense.
Ed Tanous3dac7492017-08-02 13:46:20 -070010247
10248 @complexity Logarithmic in the size of the container.
10249
10250 @liveexample{The example below shows how object elements can be read and
10251 written using the `[]` operator.,operatorarray__key_type}
10252
10253 @sa @ref at(const typename object_t::key_type&) for access by reference
10254 with range checking
10255 @sa @ref value() for access by value with a default value
10256
10257 @since version 1.1.0
10258 */
10259 template<typename T>
10260 reference operator[](T* key)
10261 {
10262 // implicitly convert null to object
10263 if (is_null())
10264 {
10265 m_type = value_t::object;
10266 m_value = value_t::object;
10267 assert_invariant();
10268 }
10269
10270 // at only works for objects
Ed Tanousba9f9a62017-10-11 16:40:35 -070010271 if (JSON_LIKELY(is_object()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010272 {
10273 return m_value.object->operator[](key);
10274 }
10275
Ed Tanousba9f9a62017-10-11 16:40:35 -070010276 JSON_THROW(type_error::create(305, "cannot use operator[] with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010277 }
10278
10279 /*!
10280 @brief read-only access specified object element
10281
10282 Returns a const reference to the element at with specified key @a key. No
10283 bounds checking is performed.
10284
10285 @warning If the element with key @a key does not exist, the behavior is
10286 undefined.
10287
10288 @param[in] key key of the element to access
10289
10290 @return const reference to the element at key @a key
10291
10292 @pre The element with key @a key must exist. **This precondition is
10293 enforced with an assertion.**
10294
Ed Tanousba9f9a62017-10-11 16:40:35 -070010295 @throw type_error.305 if the JSON value is not an object; in that cases,
10296 using the [] operator with a key makes no sense.
Ed Tanous3dac7492017-08-02 13:46:20 -070010297
10298 @complexity Logarithmic in the size of the container.
10299
10300 @liveexample{The example below shows how object elements can be read using
10301 the `[]` operator.,operatorarray__key_type_const}
10302
10303 @sa @ref at(const typename object_t::key_type&) for access by reference
10304 with range checking
10305 @sa @ref value() for access by value with a default value
10306
10307 @since version 1.1.0
10308 */
10309 template<typename T>
10310 const_reference operator[](T* key) const
10311 {
10312 // at only works for objects
Ed Tanousba9f9a62017-10-11 16:40:35 -070010313 if (JSON_LIKELY(is_object()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010314 {
10315 assert(m_value.object->find(key) != m_value.object->end());
10316 return m_value.object->find(key)->second;
10317 }
10318
Ed Tanousba9f9a62017-10-11 16:40:35 -070010319 JSON_THROW(type_error::create(305, "cannot use operator[] with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010320 }
10321
10322 /*!
10323 @brief access specified object element with default value
10324
10325 Returns either a copy of an object's element at the specified key @a key
10326 or a given default value if no element with key @a key exists.
10327
10328 The function is basically equivalent to executing
10329 @code {.cpp}
10330 try {
10331 return at(key);
Ed Tanousba9f9a62017-10-11 16:40:35 -070010332 } catch(out_of_range) {
Ed Tanous3dac7492017-08-02 13:46:20 -070010333 return default_value;
10334 }
10335 @endcode
10336
10337 @note Unlike @ref at(const typename object_t::key_type&), this function
10338 does not throw if the given key @a key was not found.
10339
10340 @note Unlike @ref operator[](const typename object_t::key_type& key), this
10341 function does not implicitly add an element to the position defined by @a
10342 key. This function is furthermore also applicable to const objects.
10343
10344 @param[in] key key of the element to access
10345 @param[in] default_value the value to return if @a key is not found
10346
10347 @tparam ValueType type compatible to JSON values, for instance `int` for
10348 JSON integer numbers, `bool` for JSON booleans, or `std::vector` types for
10349 JSON arrays. Note the type of the expected value at @a key and the default
10350 value @a default_value must be compatible.
10351
10352 @return copy of the element at key @a key or @a default_value if @a key
10353 is not found
10354
Ed Tanousba9f9a62017-10-11 16:40:35 -070010355 @throw type_error.306 if the JSON value is not an objec; in that cases,
10356 using `value()` with a key makes no sense.
Ed Tanous3dac7492017-08-02 13:46:20 -070010357
10358 @complexity Logarithmic in the size of the container.
10359
10360 @liveexample{The example below shows how object elements can be queried
10361 with a default value.,basic_json__value}
10362
10363 @sa @ref at(const typename object_t::key_type&) for access by reference
10364 with range checking
10365 @sa @ref operator[](const typename object_t::key_type&) for unchecked
10366 access by reference
10367
10368 @since version 1.0.0
10369 */
10370 template<class ValueType, typename std::enable_if<
10371 std::is_convertible<basic_json_t, ValueType>::value, int>::type = 0>
Ed Tanousba9f9a62017-10-11 16:40:35 -070010372 ValueType value(const typename object_t::key_type& key, const ValueType& default_value) const
Ed Tanous3dac7492017-08-02 13:46:20 -070010373 {
10374 // at only works for objects
Ed Tanousba9f9a62017-10-11 16:40:35 -070010375 if (JSON_LIKELY(is_object()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010376 {
10377 // if key is found, return value and given default value otherwise
10378 const auto it = find(key);
10379 if (it != end())
10380 {
10381 return *it;
10382 }
10383
10384 return default_value;
10385 }
Ed Tanousba9f9a62017-10-11 16:40:35 -070010386
10387 JSON_THROW(type_error::create(306, "cannot use value() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010388 }
10389
10390 /*!
10391 @brief overload for a default value of type const char*
10392 @copydoc basic_json::value(const typename object_t::key_type&, ValueType) const
10393 */
10394 string_t value(const typename object_t::key_type& key, const char* default_value) const
10395 {
10396 return value(key, string_t(default_value));
10397 }
10398
10399 /*!
10400 @brief access specified object element via JSON Pointer with default value
10401
10402 Returns either a copy of an object's element at the specified key @a key
10403 or a given default value if no element with key @a key exists.
10404
10405 The function is basically equivalent to executing
10406 @code {.cpp}
10407 try {
10408 return at(ptr);
Ed Tanousba9f9a62017-10-11 16:40:35 -070010409 } catch(out_of_range) {
Ed Tanous3dac7492017-08-02 13:46:20 -070010410 return default_value;
10411 }
10412 @endcode
10413
10414 @note Unlike @ref at(const json_pointer&), this function does not throw
10415 if the given key @a key was not found.
10416
10417 @param[in] ptr a JSON pointer to the element to access
10418 @param[in] default_value the value to return if @a ptr found no value
10419
10420 @tparam ValueType type compatible to JSON values, for instance `int` for
10421 JSON integer numbers, `bool` for JSON booleans, or `std::vector` types for
10422 JSON arrays. Note the type of the expected value at @a key and the default
10423 value @a default_value must be compatible.
10424
10425 @return copy of the element at key @a key or @a default_value if @a key
10426 is not found
10427
Ed Tanousba9f9a62017-10-11 16:40:35 -070010428 @throw type_error.306 if the JSON value is not an objec; in that cases,
10429 using `value()` with a key makes no sense.
Ed Tanous3dac7492017-08-02 13:46:20 -070010430
10431 @complexity Logarithmic in the size of the container.
10432
10433 @liveexample{The example below shows how object elements can be queried
10434 with a default value.,basic_json__value_ptr}
10435
10436 @sa @ref operator[](const json_pointer&) for unchecked access by reference
10437
10438 @since version 2.0.2
10439 */
10440 template<class ValueType, typename std::enable_if<
10441 std::is_convertible<basic_json_t, ValueType>::value, int>::type = 0>
Ed Tanousba9f9a62017-10-11 16:40:35 -070010442 ValueType value(const json_pointer& ptr, const ValueType& default_value) const
Ed Tanous3dac7492017-08-02 13:46:20 -070010443 {
10444 // at only works for objects
Ed Tanousba9f9a62017-10-11 16:40:35 -070010445 if (JSON_LIKELY(is_object()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010446 {
10447 // if pointer resolves a value, return it or use default value
10448 JSON_TRY
10449 {
10450 return ptr.get_checked(this);
10451 }
Ed Tanousba9f9a62017-10-11 16:40:35 -070010452 JSON_CATCH (out_of_range&)
Ed Tanous3dac7492017-08-02 13:46:20 -070010453 {
10454 return default_value;
10455 }
10456 }
10457
Ed Tanousba9f9a62017-10-11 16:40:35 -070010458 JSON_THROW(type_error::create(306, "cannot use value() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010459 }
10460
10461 /*!
10462 @brief overload for a default value of type const char*
10463 @copydoc basic_json::value(const json_pointer&, ValueType) const
10464 */
10465 string_t value(const json_pointer& ptr, const char* default_value) const
10466 {
10467 return value(ptr, string_t(default_value));
10468 }
10469
10470 /*!
10471 @brief access the first element
10472
10473 Returns a reference to the first element in the container. For a JSON
10474 container `c`, the expression `c.front()` is equivalent to `*c.begin()`.
10475
10476 @return In case of a structured type (array or object), a reference to the
10477 first element is returned. In case of number, string, or boolean values, a
10478 reference to the value is returned.
10479
10480 @complexity Constant.
10481
10482 @pre The JSON value must not be `null` (would throw `std::out_of_range`)
10483 or an empty array or object (undefined behavior, **guarded by
10484 assertions**).
10485 @post The JSON value remains unchanged.
10486
Ed Tanousba9f9a62017-10-11 16:40:35 -070010487 @throw invalid_iterator.214 when called on `null` value
Ed Tanous3dac7492017-08-02 13:46:20 -070010488
10489 @liveexample{The following code shows an example for `front()`.,front}
10490
10491 @sa @ref back() -- access the last element
10492
10493 @since version 1.0.0
10494 */
10495 reference front()
10496 {
10497 return *begin();
10498 }
10499
10500 /*!
10501 @copydoc basic_json::front()
10502 */
10503 const_reference front() const
10504 {
10505 return *cbegin();
10506 }
10507
10508 /*!
10509 @brief access the last element
10510
10511 Returns a reference to the last element in the container. For a JSON
10512 container `c`, the expression `c.back()` is equivalent to
10513 @code {.cpp}
10514 auto tmp = c.end();
10515 --tmp;
10516 return *tmp;
10517 @endcode
10518
10519 @return In case of a structured type (array or object), a reference to the
10520 last element is returned. In case of number, string, or boolean values, a
10521 reference to the value is returned.
10522
10523 @complexity Constant.
10524
10525 @pre The JSON value must not be `null` (would throw `std::out_of_range`)
10526 or an empty array or object (undefined behavior, **guarded by
10527 assertions**).
10528 @post The JSON value remains unchanged.
10529
Ed Tanousba9f9a62017-10-11 16:40:35 -070010530 @throw invalid_iterator.214 when called on a `null` value. See example
10531 below.
Ed Tanous3dac7492017-08-02 13:46:20 -070010532
10533 @liveexample{The following code shows an example for `back()`.,back}
10534
10535 @sa @ref front() -- access the first element
10536
10537 @since version 1.0.0
10538 */
10539 reference back()
10540 {
10541 auto tmp = end();
10542 --tmp;
10543 return *tmp;
10544 }
10545
10546 /*!
10547 @copydoc basic_json::back()
10548 */
10549 const_reference back() const
10550 {
10551 auto tmp = cend();
10552 --tmp;
10553 return *tmp;
10554 }
10555
10556 /*!
10557 @brief remove element given an iterator
10558
10559 Removes the element specified by iterator @a pos. The iterator @a pos must
10560 be valid and dereferenceable. Thus the `end()` iterator (which is valid,
10561 but is not dereferenceable) cannot be used as a value for @a pos.
10562
10563 If called on a primitive type other than `null`, the resulting JSON value
10564 will be `null`.
10565
10566 @param[in] pos iterator to the element to remove
10567 @return Iterator following the last removed element. If the iterator @a
10568 pos refers to the last element, the `end()` iterator is returned.
10569
10570 @tparam IteratorType an @ref iterator or @ref const_iterator
10571
10572 @post Invalidates iterators and references at or after the point of the
10573 erase, including the `end()` iterator.
10574
Ed Tanousba9f9a62017-10-11 16:40:35 -070010575 @throw type_error.307 if called on a `null` value; example: `"cannot use
10576 erase() with null"`
10577 @throw invalid_iterator.202 if called on an iterator which does not belong
10578 to the current JSON value; example: `"iterator does not fit current
10579 value"`
10580 @throw invalid_iterator.205 if called on a primitive type with invalid
Ed Tanous3dac7492017-08-02 13:46:20 -070010581 iterator (i.e., any iterator which is not `begin()`); example: `"iterator
10582 out of range"`
10583
10584 @complexity The complexity depends on the type:
10585 - objects: amortized constant
10586 - arrays: linear in distance between @a pos and the end of the container
10587 - strings: linear in the length of the string
10588 - other types: constant
10589
10590 @liveexample{The example shows the result of `erase()` for different JSON
10591 types.,erase__IteratorType}
10592
10593 @sa @ref erase(IteratorType, IteratorType) -- removes the elements in
10594 the given range
10595 @sa @ref erase(const typename object_t::key_type&) -- removes the element
10596 from an object at the given key
10597 @sa @ref erase(const size_type) -- removes the element from an array at
10598 the given index
10599
10600 @since version 1.0.0
10601 */
10602 template<class IteratorType, typename std::enable_if<
10603 std::is_same<IteratorType, typename basic_json_t::iterator>::value or
10604 std::is_same<IteratorType, typename basic_json_t::const_iterator>::value, int>::type
10605 = 0>
10606 IteratorType erase(IteratorType pos)
10607 {
10608 // make sure iterator fits the current value
Ed Tanousba9f9a62017-10-11 16:40:35 -070010609 if (JSON_UNLIKELY(this != pos.m_object))
Ed Tanous3dac7492017-08-02 13:46:20 -070010610 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070010611 JSON_THROW(invalid_iterator::create(202, "iterator does not fit current value"));
Ed Tanous3dac7492017-08-02 13:46:20 -070010612 }
10613
10614 IteratorType result = end();
10615
10616 switch (m_type)
10617 {
10618 case value_t::boolean:
10619 case value_t::number_float:
10620 case value_t::number_integer:
10621 case value_t::number_unsigned:
10622 case value_t::string:
10623 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070010624 if (JSON_UNLIKELY(not pos.m_it.primitive_iterator.is_begin()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010625 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070010626 JSON_THROW(invalid_iterator::create(205, "iterator out of range"));
Ed Tanous3dac7492017-08-02 13:46:20 -070010627 }
10628
10629 if (is_string())
10630 {
10631 AllocatorType<string_t> alloc;
10632 alloc.destroy(m_value.string);
10633 alloc.deallocate(m_value.string, 1);
10634 m_value.string = nullptr;
10635 }
10636
10637 m_type = value_t::null;
10638 assert_invariant();
10639 break;
10640 }
10641
10642 case value_t::object:
10643 {
10644 result.m_it.object_iterator = m_value.object->erase(pos.m_it.object_iterator);
10645 break;
10646 }
10647
10648 case value_t::array:
10649 {
10650 result.m_it.array_iterator = m_value.array->erase(pos.m_it.array_iterator);
10651 break;
10652 }
10653
10654 default:
Ed Tanousba9f9a62017-10-11 16:40:35 -070010655 JSON_THROW(type_error::create(307, "cannot use erase() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010656 }
10657
10658 return result;
10659 }
10660
10661 /*!
10662 @brief remove elements given an iterator range
10663
10664 Removes the element specified by the range `[first; last)`. The iterator
10665 @a first does not need to be dereferenceable if `first == last`: erasing
10666 an empty range is a no-op.
10667
10668 If called on a primitive type other than `null`, the resulting JSON value
10669 will be `null`.
10670
10671 @param[in] first iterator to the beginning of the range to remove
10672 @param[in] last iterator past the end of the range to remove
10673 @return Iterator following the last removed element. If the iterator @a
10674 second refers to the last element, the `end()` iterator is returned.
10675
10676 @tparam IteratorType an @ref iterator or @ref const_iterator
10677
10678 @post Invalidates iterators and references at or after the point of the
10679 erase, including the `end()` iterator.
10680
Ed Tanousba9f9a62017-10-11 16:40:35 -070010681 @throw type_error.307 if called on a `null` value; example: `"cannot use
10682 erase() with null"`
10683 @throw invalid_iterator.203 if called on iterators which does not belong
10684 to the current JSON value; example: `"iterators do not fit current value"`
10685 @throw invalid_iterator.204 if called on a primitive type with invalid
Ed Tanous3dac7492017-08-02 13:46:20 -070010686 iterators (i.e., if `first != begin()` and `last != end()`); example:
10687 `"iterators out of range"`
10688
10689 @complexity The complexity depends on the type:
10690 - objects: `log(size()) + std::distance(first, last)`
10691 - arrays: linear in the distance between @a first and @a last, plus linear
10692 in the distance between @a last and end of the container
10693 - strings: linear in the length of the string
10694 - other types: constant
10695
10696 @liveexample{The example shows the result of `erase()` for different JSON
10697 types.,erase__IteratorType_IteratorType}
10698
10699 @sa @ref erase(IteratorType) -- removes the element at a given position
10700 @sa @ref erase(const typename object_t::key_type&) -- removes the element
10701 from an object at the given key
10702 @sa @ref erase(const size_type) -- removes the element from an array at
10703 the given index
10704
10705 @since version 1.0.0
10706 */
10707 template<class IteratorType, typename std::enable_if<
10708 std::is_same<IteratorType, typename basic_json_t::iterator>::value or
10709 std::is_same<IteratorType, typename basic_json_t::const_iterator>::value, int>::type
10710 = 0>
10711 IteratorType erase(IteratorType first, IteratorType last)
10712 {
10713 // make sure iterator fits the current value
Ed Tanousba9f9a62017-10-11 16:40:35 -070010714 if (JSON_UNLIKELY(this != first.m_object or this != last.m_object))
Ed Tanous3dac7492017-08-02 13:46:20 -070010715 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070010716 JSON_THROW(invalid_iterator::create(203, "iterators do not fit current value"));
Ed Tanous3dac7492017-08-02 13:46:20 -070010717 }
10718
10719 IteratorType result = end();
10720
10721 switch (m_type)
10722 {
10723 case value_t::boolean:
10724 case value_t::number_float:
10725 case value_t::number_integer:
10726 case value_t::number_unsigned:
10727 case value_t::string:
10728 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070010729 if (JSON_LIKELY(not first.m_it.primitive_iterator.is_begin()
10730 or not last.m_it.primitive_iterator.is_end()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010731 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070010732 JSON_THROW(invalid_iterator::create(204, "iterators out of range"));
Ed Tanous3dac7492017-08-02 13:46:20 -070010733 }
10734
10735 if (is_string())
10736 {
10737 AllocatorType<string_t> alloc;
10738 alloc.destroy(m_value.string);
10739 alloc.deallocate(m_value.string, 1);
10740 m_value.string = nullptr;
10741 }
10742
10743 m_type = value_t::null;
10744 assert_invariant();
10745 break;
10746 }
10747
10748 case value_t::object:
10749 {
10750 result.m_it.object_iterator = m_value.object->erase(first.m_it.object_iterator,
10751 last.m_it.object_iterator);
10752 break;
10753 }
10754
10755 case value_t::array:
10756 {
10757 result.m_it.array_iterator = m_value.array->erase(first.m_it.array_iterator,
10758 last.m_it.array_iterator);
10759 break;
10760 }
10761
10762 default:
Ed Tanousba9f9a62017-10-11 16:40:35 -070010763 JSON_THROW(type_error::create(307, "cannot use erase() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010764 }
10765
10766 return result;
10767 }
10768
10769 /*!
10770 @brief remove element from a JSON object given a key
10771
10772 Removes elements from a JSON object with the key value @a key.
10773
10774 @param[in] key value of the elements to remove
10775
10776 @return Number of elements removed. If @a ObjectType is the default
10777 `std::map` type, the return value will always be `0` (@a key was not
10778 found) or `1` (@a key was found).
10779
10780 @post References and iterators to the erased elements are invalidated.
10781 Other references and iterators are not affected.
10782
Ed Tanousba9f9a62017-10-11 16:40:35 -070010783 @throw type_error.307 when called on a type other than JSON object;
Ed Tanous3dac7492017-08-02 13:46:20 -070010784 example: `"cannot use erase() with null"`
10785
10786 @complexity `log(size()) + count(key)`
10787
10788 @liveexample{The example shows the effect of `erase()`.,erase__key_type}
10789
10790 @sa @ref erase(IteratorType) -- removes the element at a given position
10791 @sa @ref erase(IteratorType, IteratorType) -- removes the elements in
10792 the given range
10793 @sa @ref erase(const size_type) -- removes the element from an array at
10794 the given index
10795
10796 @since version 1.0.0
10797 */
10798 size_type erase(const typename object_t::key_type& key)
10799 {
10800 // this erase only works for objects
Ed Tanousba9f9a62017-10-11 16:40:35 -070010801 if (JSON_LIKELY(is_object()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010802 {
10803 return m_value.object->erase(key);
10804 }
10805
Ed Tanousba9f9a62017-10-11 16:40:35 -070010806 JSON_THROW(type_error::create(307, "cannot use erase() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010807 }
10808
10809 /*!
10810 @brief remove element from a JSON array given an index
10811
10812 Removes element from a JSON array at the index @a idx.
10813
10814 @param[in] idx index of the element to remove
10815
Ed Tanousba9f9a62017-10-11 16:40:35 -070010816 @throw type_error.307 when called on a type other than JSON object;
Ed Tanous3dac7492017-08-02 13:46:20 -070010817 example: `"cannot use erase() with null"`
Ed Tanousba9f9a62017-10-11 16:40:35 -070010818 @throw out_of_range.401 when `idx >= size()`; example: `"array index 17
Ed Tanous3dac7492017-08-02 13:46:20 -070010819 is out of range"`
10820
10821 @complexity Linear in distance between @a idx and the end of the container.
10822
10823 @liveexample{The example shows the effect of `erase()`.,erase__size_type}
10824
10825 @sa @ref erase(IteratorType) -- removes the element at a given position
10826 @sa @ref erase(IteratorType, IteratorType) -- removes the elements in
10827 the given range
10828 @sa @ref erase(const typename object_t::key_type&) -- removes the element
10829 from an object at the given key
10830
10831 @since version 1.0.0
10832 */
10833 void erase(const size_type idx)
10834 {
10835 // this erase only works for arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -070010836 if (JSON_LIKELY(is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010837 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070010838 if (JSON_UNLIKELY(idx >= size()))
Ed Tanous3dac7492017-08-02 13:46:20 -070010839 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070010840 JSON_THROW(out_of_range::create(401, "array index " + std::to_string(idx) + " is out of range"));
Ed Tanous3dac7492017-08-02 13:46:20 -070010841 }
10842
10843 m_value.array->erase(m_value.array->begin() + static_cast<difference_type>(idx));
10844 }
10845 else
10846 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070010847 JSON_THROW(type_error::create(307, "cannot use erase() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070010848 }
10849 }
10850
10851 /// @}
10852
10853
10854 ////////////
10855 // lookup //
10856 ////////////
10857
10858 /// @name lookup
10859 /// @{
10860
10861 /*!
10862 @brief find an element in a JSON object
10863
10864 Finds an element in a JSON object with key equivalent to @a key. If the
10865 element is not found or the JSON value is not an object, end() is
10866 returned.
10867
10868 @note This method always returns @ref end() when executed on a JSON type
10869 that is not an object.
10870
10871 @param[in] key key value of the element to search for
10872
10873 @return Iterator to an element with key equivalent to @a key. If no such
10874 element is found or the JSON value is not an object, past-the-end (see
10875 @ref end()) iterator is returned.
10876
10877 @complexity Logarithmic in the size of the JSON object.
10878
10879 @liveexample{The example shows how `find()` is used.,find__key_type}
10880
10881 @since version 1.0.0
10882 */
10883 iterator find(typename object_t::key_type key)
10884 {
10885 auto result = end();
10886
10887 if (is_object())
10888 {
10889 result.m_it.object_iterator = m_value.object->find(key);
10890 }
10891
10892 return result;
10893 }
10894
10895 /*!
10896 @brief find an element in a JSON object
10897 @copydoc find(typename object_t::key_type)
10898 */
10899 const_iterator find(typename object_t::key_type key) const
10900 {
10901 auto result = cend();
10902
10903 if (is_object())
10904 {
10905 result.m_it.object_iterator = m_value.object->find(key);
10906 }
10907
10908 return result;
10909 }
10910
10911 /*!
10912 @brief returns the number of occurrences of a key in a JSON object
10913
10914 Returns the number of elements with key @a key. If ObjectType is the
10915 default `std::map` type, the return value will always be `0` (@a key was
10916 not found) or `1` (@a key was found).
10917
10918 @note This method always returns `0` when executed on a JSON type that is
10919 not an object.
10920
10921 @param[in] key key value of the element to count
10922
10923 @return Number of elements with key @a key. If the JSON value is not an
10924 object, the return value will be `0`.
10925
10926 @complexity Logarithmic in the size of the JSON object.
10927
10928 @liveexample{The example shows how `count()` is used.,count}
10929
10930 @since version 1.0.0
10931 */
10932 size_type count(typename object_t::key_type key) const
10933 {
10934 // return 0 for all nonobject types
10935 return is_object() ? m_value.object->count(key) : 0;
10936 }
10937
10938 /// @}
10939
10940
10941 ///////////////
10942 // iterators //
10943 ///////////////
10944
10945 /// @name iterators
10946 /// @{
10947
10948 /*!
10949 @brief returns an iterator to the first element
10950
10951 Returns an iterator to the first element.
10952
10953 @image html range-begin-end.svg "Illustration from cppreference.com"
10954
10955 @return iterator to the first element
10956
10957 @complexity Constant.
10958
10959 @requirement This function helps `basic_json` satisfying the
10960 [Container](http://en.cppreference.com/w/cpp/concept/Container)
10961 requirements:
10962 - The complexity is constant.
10963
10964 @liveexample{The following code shows an example for `begin()`.,begin}
10965
10966 @sa @ref cbegin() -- returns a const iterator to the beginning
10967 @sa @ref end() -- returns an iterator to the end
10968 @sa @ref cend() -- returns a const iterator to the end
10969
10970 @since version 1.0.0
10971 */
10972 iterator begin() noexcept
10973 {
10974 iterator result(this);
10975 result.set_begin();
10976 return result;
10977 }
10978
10979 /*!
10980 @copydoc basic_json::cbegin()
10981 */
10982 const_iterator begin() const noexcept
10983 {
10984 return cbegin();
10985 }
10986
10987 /*!
10988 @brief returns a const iterator to the first element
10989
10990 Returns a const iterator to the first element.
10991
10992 @image html range-begin-end.svg "Illustration from cppreference.com"
10993
10994 @return const iterator to the first element
10995
10996 @complexity Constant.
10997
10998 @requirement This function helps `basic_json` satisfying the
10999 [Container](http://en.cppreference.com/w/cpp/concept/Container)
11000 requirements:
11001 - The complexity is constant.
11002 - Has the semantics of `const_cast<const basic_json&>(*this).begin()`.
11003
11004 @liveexample{The following code shows an example for `cbegin()`.,cbegin}
11005
11006 @sa @ref begin() -- returns an iterator to the beginning
11007 @sa @ref end() -- returns an iterator to the end
11008 @sa @ref cend() -- returns a const iterator to the end
11009
11010 @since version 1.0.0
11011 */
11012 const_iterator cbegin() const noexcept
11013 {
11014 const_iterator result(this);
11015 result.set_begin();
11016 return result;
11017 }
11018
11019 /*!
11020 @brief returns an iterator to one past the last element
11021
11022 Returns an iterator to one past the last element.
11023
11024 @image html range-begin-end.svg "Illustration from cppreference.com"
11025
11026 @return iterator one past the last element
11027
11028 @complexity Constant.
11029
11030 @requirement This function helps `basic_json` satisfying the
11031 [Container](http://en.cppreference.com/w/cpp/concept/Container)
11032 requirements:
11033 - The complexity is constant.
11034
11035 @liveexample{The following code shows an example for `end()`.,end}
11036
11037 @sa @ref cend() -- returns a const iterator to the end
11038 @sa @ref begin() -- returns an iterator to the beginning
11039 @sa @ref cbegin() -- returns a const iterator to the beginning
11040
11041 @since version 1.0.0
11042 */
11043 iterator end() noexcept
11044 {
11045 iterator result(this);
11046 result.set_end();
11047 return result;
11048 }
11049
11050 /*!
11051 @copydoc basic_json::cend()
11052 */
11053 const_iterator end() const noexcept
11054 {
11055 return cend();
11056 }
11057
11058 /*!
11059 @brief returns a const iterator to one past the last element
11060
11061 Returns a const iterator to one past the last element.
11062
11063 @image html range-begin-end.svg "Illustration from cppreference.com"
11064
11065 @return const iterator one past the last element
11066
11067 @complexity Constant.
11068
11069 @requirement This function helps `basic_json` satisfying the
11070 [Container](http://en.cppreference.com/w/cpp/concept/Container)
11071 requirements:
11072 - The complexity is constant.
11073 - Has the semantics of `const_cast<const basic_json&>(*this).end()`.
11074
11075 @liveexample{The following code shows an example for `cend()`.,cend}
11076
11077 @sa @ref end() -- returns an iterator to the end
11078 @sa @ref begin() -- returns an iterator to the beginning
11079 @sa @ref cbegin() -- returns a const iterator to the beginning
11080
11081 @since version 1.0.0
11082 */
11083 const_iterator cend() const noexcept
11084 {
11085 const_iterator result(this);
11086 result.set_end();
11087 return result;
11088 }
11089
11090 /*!
11091 @brief returns an iterator to the reverse-beginning
11092
11093 Returns an iterator to the reverse-beginning; that is, the last element.
11094
11095 @image html range-rbegin-rend.svg "Illustration from cppreference.com"
11096
11097 @complexity Constant.
11098
11099 @requirement This function helps `basic_json` satisfying the
11100 [ReversibleContainer](http://en.cppreference.com/w/cpp/concept/ReversibleContainer)
11101 requirements:
11102 - The complexity is constant.
11103 - Has the semantics of `reverse_iterator(end())`.
11104
11105 @liveexample{The following code shows an example for `rbegin()`.,rbegin}
11106
11107 @sa @ref crbegin() -- returns a const reverse iterator to the beginning
11108 @sa @ref rend() -- returns a reverse iterator to the end
11109 @sa @ref crend() -- returns a const reverse iterator to the end
11110
11111 @since version 1.0.0
11112 */
11113 reverse_iterator rbegin() noexcept
11114 {
11115 return reverse_iterator(end());
11116 }
11117
11118 /*!
11119 @copydoc basic_json::crbegin()
11120 */
11121 const_reverse_iterator rbegin() const noexcept
11122 {
11123 return crbegin();
11124 }
11125
11126 /*!
11127 @brief returns an iterator to the reverse-end
11128
11129 Returns an iterator to the reverse-end; that is, one before the first
11130 element.
11131
11132 @image html range-rbegin-rend.svg "Illustration from cppreference.com"
11133
11134 @complexity Constant.
11135
11136 @requirement This function helps `basic_json` satisfying the
11137 [ReversibleContainer](http://en.cppreference.com/w/cpp/concept/ReversibleContainer)
11138 requirements:
11139 - The complexity is constant.
11140 - Has the semantics of `reverse_iterator(begin())`.
11141
11142 @liveexample{The following code shows an example for `rend()`.,rend}
11143
11144 @sa @ref crend() -- returns a const reverse iterator to the end
11145 @sa @ref rbegin() -- returns a reverse iterator to the beginning
11146 @sa @ref crbegin() -- returns a const reverse iterator to the beginning
11147
11148 @since version 1.0.0
11149 */
11150 reverse_iterator rend() noexcept
11151 {
11152 return reverse_iterator(begin());
11153 }
11154
11155 /*!
11156 @copydoc basic_json::crend()
11157 */
11158 const_reverse_iterator rend() const noexcept
11159 {
11160 return crend();
11161 }
11162
11163 /*!
11164 @brief returns a const reverse iterator to the last element
11165
11166 Returns a const iterator to the reverse-beginning; that is, the last
11167 element.
11168
11169 @image html range-rbegin-rend.svg "Illustration from cppreference.com"
11170
11171 @complexity Constant.
11172
11173 @requirement This function helps `basic_json` satisfying the
11174 [ReversibleContainer](http://en.cppreference.com/w/cpp/concept/ReversibleContainer)
11175 requirements:
11176 - The complexity is constant.
11177 - Has the semantics of `const_cast<const basic_json&>(*this).rbegin()`.
11178
11179 @liveexample{The following code shows an example for `crbegin()`.,crbegin}
11180
11181 @sa @ref rbegin() -- returns a reverse iterator to the beginning
11182 @sa @ref rend() -- returns a reverse iterator to the end
11183 @sa @ref crend() -- returns a const reverse iterator to the end
11184
11185 @since version 1.0.0
11186 */
11187 const_reverse_iterator crbegin() const noexcept
11188 {
11189 return const_reverse_iterator(cend());
11190 }
11191
11192 /*!
11193 @brief returns a const reverse iterator to one before the first
11194
11195 Returns a const reverse iterator to the reverse-end; that is, one before
11196 the first element.
11197
11198 @image html range-rbegin-rend.svg "Illustration from cppreference.com"
11199
11200 @complexity Constant.
11201
11202 @requirement This function helps `basic_json` satisfying the
11203 [ReversibleContainer](http://en.cppreference.com/w/cpp/concept/ReversibleContainer)
11204 requirements:
11205 - The complexity is constant.
11206 - Has the semantics of `const_cast<const basic_json&>(*this).rend()`.
11207
11208 @liveexample{The following code shows an example for `crend()`.,crend}
11209
11210 @sa @ref rend() -- returns a reverse iterator to the end
11211 @sa @ref rbegin() -- returns a reverse iterator to the beginning
11212 @sa @ref crbegin() -- returns a const reverse iterator to the beginning
11213
11214 @since version 1.0.0
11215 */
11216 const_reverse_iterator crend() const noexcept
11217 {
11218 return const_reverse_iterator(cbegin());
11219 }
11220
Ed Tanous3dac7492017-08-02 13:46:20 -070011221 public:
11222 /*!
11223 @brief wrapper to access iterator member functions in range-based for
11224
11225 This function allows to access @ref iterator::key() and @ref
11226 iterator::value() during range-based for loops. In these loops, a
11227 reference to the JSON values is returned, so there is no access to the
11228 underlying iterator.
11229
Ed Tanousba9f9a62017-10-11 16:40:35 -070011230 @liveexample{The following code shows how the wrapper is used,iterator_wrapper}
11231
Ed Tanous3dac7492017-08-02 13:46:20 -070011232 @note The name of this function is not yet final and may change in the
11233 future.
11234 */
11235 static iteration_proxy<iterator> iterator_wrapper(reference cont)
11236 {
11237 return iteration_proxy<iterator>(cont);
11238 }
11239
11240 /*!
11241 @copydoc iterator_wrapper(reference)
11242 */
11243 static iteration_proxy<const_iterator> iterator_wrapper(const_reference cont)
11244 {
11245 return iteration_proxy<const_iterator>(cont);
11246 }
11247
11248 /// @}
11249
11250
11251 //////////////
11252 // capacity //
11253 //////////////
11254
11255 /// @name capacity
11256 /// @{
11257
11258 /*!
Ed Tanousba9f9a62017-10-11 16:40:35 -070011259 @brief checks whether the container is empty.
Ed Tanous3dac7492017-08-02 13:46:20 -070011260
Ed Tanousba9f9a62017-10-11 16:40:35 -070011261 Checks if a JSON value has no elements (i.e. whether its @ref size is `0`).
Ed Tanous3dac7492017-08-02 13:46:20 -070011262
11263 @return The return value depends on the different types and is
11264 defined as follows:
11265 Value type | return value
11266 ----------- | -------------
11267 null | `true`
11268 boolean | `false`
11269 string | `false`
11270 number | `false`
11271 object | result of function `object_t::empty()`
11272 array | result of function `array_t::empty()`
11273
Ed Tanousba9f9a62017-10-11 16:40:35 -070011274 @liveexample{The following code uses `empty()` to check if a JSON
11275 object contains any elements.,empty}
Ed Tanous3dac7492017-08-02 13:46:20 -070011276
11277 @complexity Constant, as long as @ref array_t and @ref object_t satisfy
11278 the Container concept; that is, their `empty()` functions have constant
11279 complexity.
11280
Ed Tanousba9f9a62017-10-11 16:40:35 -070011281 @iterators No changes.
11282
11283 @exceptionsafety No-throw guarantee: this function never throws exceptions.
11284
11285 @note This function does not return whether a string stored as JSON value
11286 is empty - it returns whether the JSON container itself is empty which is
11287 false in the case of a string.
11288
Ed Tanous3dac7492017-08-02 13:46:20 -070011289 @requirement This function helps `basic_json` satisfying the
11290 [Container](http://en.cppreference.com/w/cpp/concept/Container)
11291 requirements:
11292 - The complexity is constant.
11293 - Has the semantics of `begin() == end()`.
11294
Ed Tanous3dac7492017-08-02 13:46:20 -070011295 @sa @ref size() -- returns the number of elements
11296
11297 @since version 1.0.0
11298 */
11299 bool empty() const noexcept
11300 {
11301 switch (m_type)
11302 {
11303 case value_t::null:
11304 {
11305 // null values are empty
11306 return true;
11307 }
11308
11309 case value_t::array:
11310 {
11311 // delegate call to array_t::empty()
11312 return m_value.array->empty();
11313 }
11314
11315 case value_t::object:
11316 {
11317 // delegate call to object_t::empty()
11318 return m_value.object->empty();
11319 }
11320
11321 default:
11322 {
11323 // all other types are nonempty
11324 return false;
11325 }
11326 }
11327 }
11328
11329 /*!
11330 @brief returns the number of elements
11331
11332 Returns the number of elements in a JSON value.
11333
11334 @return The return value depends on the different types and is
11335 defined as follows:
11336 Value type | return value
11337 ----------- | -------------
11338 null | `0`
11339 boolean | `1`
11340 string | `1`
11341 number | `1`
11342 object | result of function object_t::size()
11343 array | result of function array_t::size()
11344
Ed Tanousba9f9a62017-10-11 16:40:35 -070011345 @liveexample{The following code calls `size()` on the different value
11346 types.,size}
Ed Tanous3dac7492017-08-02 13:46:20 -070011347
11348 @complexity Constant, as long as @ref array_t and @ref object_t satisfy
11349 the Container concept; that is, their size() functions have constant
11350 complexity.
11351
Ed Tanousba9f9a62017-10-11 16:40:35 -070011352 @iterators No changes.
11353
11354 @exceptionsafety No-throw guarantee: this function never throws exceptions.
11355
11356 @note This function does not return the length of a string stored as JSON
11357 value - it returns the number of elements in the JSON value which is 1 in
11358 the case of a string.
11359
Ed Tanous3dac7492017-08-02 13:46:20 -070011360 @requirement This function helps `basic_json` satisfying the
11361 [Container](http://en.cppreference.com/w/cpp/concept/Container)
11362 requirements:
11363 - The complexity is constant.
11364 - Has the semantics of `std::distance(begin(), end())`.
11365
Ed Tanous3dac7492017-08-02 13:46:20 -070011366 @sa @ref empty() -- checks whether the container is empty
11367 @sa @ref max_size() -- returns the maximal number of elements
11368
11369 @since version 1.0.0
11370 */
11371 size_type size() const noexcept
11372 {
11373 switch (m_type)
11374 {
11375 case value_t::null:
11376 {
11377 // null values are empty
11378 return 0;
11379 }
11380
11381 case value_t::array:
11382 {
11383 // delegate call to array_t::size()
11384 return m_value.array->size();
11385 }
11386
11387 case value_t::object:
11388 {
11389 // delegate call to object_t::size()
11390 return m_value.object->size();
11391 }
11392
11393 default:
11394 {
11395 // all other types have size 1
11396 return 1;
11397 }
11398 }
11399 }
11400
11401 /*!
11402 @brief returns the maximum possible number of elements
11403
11404 Returns the maximum number of elements a JSON value is able to hold due to
11405 system or library implementation limitations, i.e. `std::distance(begin(),
11406 end())` for the JSON value.
11407
11408 @return The return value depends on the different types and is
11409 defined as follows:
11410 Value type | return value
11411 ----------- | -------------
11412 null | `0` (same as `size()`)
11413 boolean | `1` (same as `size()`)
11414 string | `1` (same as `size()`)
11415 number | `1` (same as `size()`)
11416 object | result of function `object_t::max_size()`
11417 array | result of function `array_t::max_size()`
11418
Ed Tanousba9f9a62017-10-11 16:40:35 -070011419 @liveexample{The following code calls `max_size()` on the different value
11420 types. Note the output is implementation specific.,max_size}
11421
Ed Tanous3dac7492017-08-02 13:46:20 -070011422 @complexity Constant, as long as @ref array_t and @ref object_t satisfy
11423 the Container concept; that is, their `max_size()` functions have constant
11424 complexity.
11425
Ed Tanousba9f9a62017-10-11 16:40:35 -070011426 @iterators No changes.
11427
11428 @exceptionsafety No-throw guarantee: this function never throws exceptions.
11429
Ed Tanous3dac7492017-08-02 13:46:20 -070011430 @requirement This function helps `basic_json` satisfying the
11431 [Container](http://en.cppreference.com/w/cpp/concept/Container)
11432 requirements:
11433 - The complexity is constant.
11434 - Has the semantics of returning `b.size()` where `b` is the largest
11435 possible JSON value.
11436
Ed Tanous3dac7492017-08-02 13:46:20 -070011437 @sa @ref size() -- returns the number of elements
11438
11439 @since version 1.0.0
11440 */
11441 size_type max_size() const noexcept
11442 {
11443 switch (m_type)
11444 {
11445 case value_t::array:
11446 {
11447 // delegate call to array_t::max_size()
11448 return m_value.array->max_size();
11449 }
11450
11451 case value_t::object:
11452 {
11453 // delegate call to object_t::max_size()
11454 return m_value.object->max_size();
11455 }
11456
11457 default:
11458 {
11459 // all other types have max_size() == size()
11460 return size();
11461 }
11462 }
11463 }
11464
11465 /// @}
11466
11467
11468 ///////////////
11469 // modifiers //
11470 ///////////////
11471
11472 /// @name modifiers
11473 /// @{
11474
11475 /*!
11476 @brief clears the contents
11477
11478 Clears the content of a JSON value and resets it to the default value as
Ed Tanousba9f9a62017-10-11 16:40:35 -070011479 if @ref basic_json(value_t) would have been called with the current value
11480 type from @ref type():
Ed Tanous3dac7492017-08-02 13:46:20 -070011481
11482 Value type | initial value
11483 ----------- | -------------
11484 null | `null`
11485 boolean | `false`
11486 string | `""`
11487 number | `0`
11488 object | `{}`
11489 array | `[]`
11490
Ed Tanousba9f9a62017-10-11 16:40:35 -070011491 @post Has the same effect as calling
11492 @code {.cpp}
11493 *this = basic_json(type());
11494 @endcode
Ed Tanous3dac7492017-08-02 13:46:20 -070011495
11496 @liveexample{The example below shows the effect of `clear()` to different
11497 JSON types.,clear}
11498
Ed Tanousba9f9a62017-10-11 16:40:35 -070011499 @complexity Linear in the size of the JSON value.
11500
11501 @iterators All iterators, pointers and references related to this container
11502 are invalidated.
11503
11504 @exceptionsafety No-throw guarantee: this function never throws exceptions.
11505
11506 @sa @ref basic_json(value_t) -- constructor that creates an object with the
11507 same value than calling `clear()`
11508
Ed Tanous3dac7492017-08-02 13:46:20 -070011509 @since version 1.0.0
11510 */
11511 void clear() noexcept
11512 {
11513 switch (m_type)
11514 {
11515 case value_t::number_integer:
11516 {
11517 m_value.number_integer = 0;
11518 break;
11519 }
11520
11521 case value_t::number_unsigned:
11522 {
11523 m_value.number_unsigned = 0;
11524 break;
11525 }
11526
11527 case value_t::number_float:
11528 {
11529 m_value.number_float = 0.0;
11530 break;
11531 }
11532
11533 case value_t::boolean:
11534 {
11535 m_value.boolean = false;
11536 break;
11537 }
11538
11539 case value_t::string:
11540 {
11541 m_value.string->clear();
11542 break;
11543 }
11544
11545 case value_t::array:
11546 {
11547 m_value.array->clear();
11548 break;
11549 }
11550
11551 case value_t::object:
11552 {
11553 m_value.object->clear();
11554 break;
11555 }
11556
11557 default:
Ed Tanous3dac7492017-08-02 13:46:20 -070011558 break;
Ed Tanous3dac7492017-08-02 13:46:20 -070011559 }
11560 }
11561
11562 /*!
11563 @brief add an object to an array
11564
11565 Appends the given element @a val to the end of the JSON value. If the
11566 function is called on a JSON null value, an empty array is created before
11567 appending @a val.
11568
11569 @param[in] val the value to add to the JSON array
11570
Ed Tanousba9f9a62017-10-11 16:40:35 -070011571 @throw type_error.308 when called on a type other than JSON array or
Ed Tanous3dac7492017-08-02 13:46:20 -070011572 null; example: `"cannot use push_back() with number"`
11573
11574 @complexity Amortized constant.
11575
11576 @liveexample{The example shows how `push_back()` and `+=` can be used to
11577 add elements to a JSON array. Note how the `null` value was silently
11578 converted to a JSON array.,push_back}
11579
11580 @since version 1.0.0
11581 */
11582 void push_back(basic_json&& val)
11583 {
11584 // push_back only works for null objects or arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -070011585 if (JSON_UNLIKELY(not(is_null() or is_array())))
Ed Tanous3dac7492017-08-02 13:46:20 -070011586 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070011587 JSON_THROW(type_error::create(308, "cannot use push_back() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070011588 }
11589
11590 // transform null object into an array
11591 if (is_null())
11592 {
11593 m_type = value_t::array;
11594 m_value = value_t::array;
11595 assert_invariant();
11596 }
11597
11598 // add element to array (move semantics)
11599 m_value.array->push_back(std::move(val));
11600 // invalidate object
11601 val.m_type = value_t::null;
11602 }
11603
11604 /*!
11605 @brief add an object to an array
11606 @copydoc push_back(basic_json&&)
11607 */
11608 reference operator+=(basic_json&& val)
11609 {
11610 push_back(std::move(val));
11611 return *this;
11612 }
11613
11614 /*!
11615 @brief add an object to an array
11616 @copydoc push_back(basic_json&&)
11617 */
11618 void push_back(const basic_json& val)
11619 {
11620 // push_back only works for null objects or arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -070011621 if (JSON_UNLIKELY(not(is_null() or is_array())))
Ed Tanous3dac7492017-08-02 13:46:20 -070011622 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070011623 JSON_THROW(type_error::create(308, "cannot use push_back() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070011624 }
11625
11626 // transform null object into an array
11627 if (is_null())
11628 {
11629 m_type = value_t::array;
11630 m_value = value_t::array;
11631 assert_invariant();
11632 }
11633
11634 // add element to array
11635 m_value.array->push_back(val);
11636 }
11637
11638 /*!
11639 @brief add an object to an array
11640 @copydoc push_back(basic_json&&)
11641 */
11642 reference operator+=(const basic_json& val)
11643 {
11644 push_back(val);
11645 return *this;
11646 }
11647
11648 /*!
11649 @brief add an object to an object
11650
11651 Inserts the given element @a val to the JSON object. If the function is
11652 called on a JSON null value, an empty object is created before inserting
11653 @a val.
11654
11655 @param[in] val the value to add to the JSON object
11656
Ed Tanousba9f9a62017-10-11 16:40:35 -070011657 @throw type_error.308 when called on a type other than JSON object or
Ed Tanous3dac7492017-08-02 13:46:20 -070011658 null; example: `"cannot use push_back() with number"`
11659
11660 @complexity Logarithmic in the size of the container, O(log(`size()`)).
11661
11662 @liveexample{The example shows how `push_back()` and `+=` can be used to
11663 add elements to a JSON object. Note how the `null` value was silently
11664 converted to a JSON object.,push_back__object_t__value}
11665
11666 @since version 1.0.0
11667 */
11668 void push_back(const typename object_t::value_type& val)
11669 {
11670 // push_back only works for null objects or objects
Ed Tanousba9f9a62017-10-11 16:40:35 -070011671 if (JSON_UNLIKELY(not(is_null() or is_object())))
Ed Tanous3dac7492017-08-02 13:46:20 -070011672 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070011673 JSON_THROW(type_error::create(308, "cannot use push_back() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070011674 }
11675
11676 // transform null object into an object
11677 if (is_null())
11678 {
11679 m_type = value_t::object;
11680 m_value = value_t::object;
11681 assert_invariant();
11682 }
11683
11684 // add element to array
11685 m_value.object->insert(val);
11686 }
11687
11688 /*!
11689 @brief add an object to an object
11690 @copydoc push_back(const typename object_t::value_type&)
11691 */
11692 reference operator+=(const typename object_t::value_type& val)
11693 {
11694 push_back(val);
11695 return *this;
11696 }
11697
11698 /*!
11699 @brief add an object to an object
11700
11701 This function allows to use `push_back` with an initializer list. In case
11702
11703 1. the current value is an object,
11704 2. the initializer list @a init contains only two elements, and
11705 3. the first element of @a init is a string,
11706
11707 @a init is converted into an object element and added using
11708 @ref push_back(const typename object_t::value_type&). Otherwise, @a init
11709 is converted to a JSON value and added using @ref push_back(basic_json&&).
11710
Ed Tanousba9f9a62017-10-11 16:40:35 -070011711 @param[in] init an initializer list
Ed Tanous3dac7492017-08-02 13:46:20 -070011712
11713 @complexity Linear in the size of the initializer list @a init.
11714
11715 @note This function is required to resolve an ambiguous overload error,
11716 because pairs like `{"key", "value"}` can be both interpreted as
11717 `object_t::value_type` or `std::initializer_list<basic_json>`, see
11718 https://github.com/nlohmann/json/issues/235 for more information.
11719
11720 @liveexample{The example shows how initializer lists are treated as
11721 objects when possible.,push_back__initializer_list}
11722 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070011723 void push_back(initializer_list_t init)
Ed Tanous3dac7492017-08-02 13:46:20 -070011724 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070011725 if (is_object() and init.size() == 2 and (*init.begin())->is_string())
Ed Tanous3dac7492017-08-02 13:46:20 -070011726 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070011727 basic_json&& key = init.begin()->moved_or_copied();
11728 push_back(typename object_t::value_type(
11729 std::move(key.get_ref<string_t&>()), (init.begin() + 1)->moved_or_copied()));
Ed Tanous3dac7492017-08-02 13:46:20 -070011730 }
11731 else
11732 {
11733 push_back(basic_json(init));
11734 }
11735 }
11736
11737 /*!
11738 @brief add an object to an object
Ed Tanousba9f9a62017-10-11 16:40:35 -070011739 @copydoc push_back(initializer_list_t)
Ed Tanous3dac7492017-08-02 13:46:20 -070011740 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070011741 reference operator+=(initializer_list_t init)
Ed Tanous3dac7492017-08-02 13:46:20 -070011742 {
11743 push_back(init);
11744 return *this;
11745 }
11746
11747 /*!
11748 @brief add an object to an array
11749
11750 Creates a JSON value from the passed parameters @a args to the end of the
11751 JSON value. If the function is called on a JSON null value, an empty array
11752 is created before appending the value created from @a args.
11753
11754 @param[in] args arguments to forward to a constructor of @ref basic_json
11755 @tparam Args compatible types to create a @ref basic_json object
11756
Ed Tanousba9f9a62017-10-11 16:40:35 -070011757 @throw type_error.311 when called on a type other than JSON array or
Ed Tanous3dac7492017-08-02 13:46:20 -070011758 null; example: `"cannot use emplace_back() with number"`
11759
11760 @complexity Amortized constant.
11761
11762 @liveexample{The example shows how `push_back()` can be used to add
11763 elements to a JSON array. Note how the `null` value was silently converted
11764 to a JSON array.,emplace_back}
11765
11766 @since version 2.0.8
11767 */
11768 template<class... Args>
11769 void emplace_back(Args&& ... args)
11770 {
11771 // emplace_back only works for null objects or arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -070011772 if (JSON_UNLIKELY(not(is_null() or is_array())))
Ed Tanous3dac7492017-08-02 13:46:20 -070011773 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070011774 JSON_THROW(type_error::create(311, "cannot use emplace_back() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070011775 }
11776
11777 // transform null object into an array
11778 if (is_null())
11779 {
11780 m_type = value_t::array;
11781 m_value = value_t::array;
11782 assert_invariant();
11783 }
11784
11785 // add element to array (perfect forwarding)
11786 m_value.array->emplace_back(std::forward<Args>(args)...);
11787 }
11788
11789 /*!
11790 @brief add an object to an object if key does not exist
11791
11792 Inserts a new element into a JSON object constructed in-place with the
11793 given @a args if there is no element with the key in the container. If the
11794 function is called on a JSON null value, an empty object is created before
11795 appending the value created from @a args.
11796
11797 @param[in] args arguments to forward to a constructor of @ref basic_json
11798 @tparam Args compatible types to create a @ref basic_json object
11799
11800 @return a pair consisting of an iterator to the inserted element, or the
11801 already-existing element if no insertion happened, and a bool
11802 denoting whether the insertion took place.
11803
Ed Tanousba9f9a62017-10-11 16:40:35 -070011804 @throw type_error.311 when called on a type other than JSON object or
Ed Tanous3dac7492017-08-02 13:46:20 -070011805 null; example: `"cannot use emplace() with number"`
11806
11807 @complexity Logarithmic in the size of the container, O(log(`size()`)).
11808
11809 @liveexample{The example shows how `emplace()` can be used to add elements
11810 to a JSON object. Note how the `null` value was silently converted to a
11811 JSON object. Further note how no value is added if there was already one
11812 value stored with the same key.,emplace}
11813
11814 @since version 2.0.8
11815 */
11816 template<class... Args>
11817 std::pair<iterator, bool> emplace(Args&& ... args)
11818 {
11819 // emplace only works for null objects or arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -070011820 if (JSON_UNLIKELY(not(is_null() or is_object())))
Ed Tanous3dac7492017-08-02 13:46:20 -070011821 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070011822 JSON_THROW(type_error::create(311, "cannot use emplace() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070011823 }
11824
11825 // transform null object into an object
11826 if (is_null())
11827 {
11828 m_type = value_t::object;
11829 m_value = value_t::object;
11830 assert_invariant();
11831 }
11832
11833 // add element to array (perfect forwarding)
11834 auto res = m_value.object->emplace(std::forward<Args>(args)...);
11835 // create result iterator and set iterator to the result of emplace
11836 auto it = begin();
11837 it.m_it.object_iterator = res.first;
11838
11839 // return pair of iterator and boolean
11840 return {it, res.second};
11841 }
11842
11843 /*!
11844 @brief inserts element
11845
11846 Inserts element @a val before iterator @a pos.
11847
11848 @param[in] pos iterator before which the content will be inserted; may be
11849 the end() iterator
11850 @param[in] val element to insert
11851 @return iterator pointing to the inserted @a val.
11852
Ed Tanousba9f9a62017-10-11 16:40:35 -070011853 @throw type_error.309 if called on JSON values other than arrays;
Ed Tanous3dac7492017-08-02 13:46:20 -070011854 example: `"cannot use insert() with string"`
Ed Tanousba9f9a62017-10-11 16:40:35 -070011855 @throw invalid_iterator.202 if @a pos is not an iterator of *this;
11856 example: `"iterator does not fit current value"`
Ed Tanous3dac7492017-08-02 13:46:20 -070011857
11858 @complexity Constant plus linear in the distance between @a pos and end of
11859 the container.
11860
11861 @liveexample{The example shows how `insert()` is used.,insert}
11862
11863 @since version 1.0.0
11864 */
11865 iterator insert(const_iterator pos, const basic_json& val)
11866 {
11867 // insert only works for arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -070011868 if (JSON_LIKELY(is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -070011869 {
11870 // check if iterator pos fits to this JSON value
Ed Tanousba9f9a62017-10-11 16:40:35 -070011871 if (JSON_UNLIKELY(pos.m_object != this))
Ed Tanous3dac7492017-08-02 13:46:20 -070011872 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070011873 JSON_THROW(invalid_iterator::create(202, "iterator does not fit current value"));
Ed Tanous3dac7492017-08-02 13:46:20 -070011874 }
11875
11876 // insert to array and return iterator
11877 iterator result(this);
11878 result.m_it.array_iterator = m_value.array->insert(pos.m_it.array_iterator, val);
11879 return result;
11880 }
11881
Ed Tanousba9f9a62017-10-11 16:40:35 -070011882 JSON_THROW(type_error::create(309, "cannot use insert() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070011883 }
11884
11885 /*!
11886 @brief inserts element
11887 @copydoc insert(const_iterator, const basic_json&)
11888 */
11889 iterator insert(const_iterator pos, basic_json&& val)
11890 {
11891 return insert(pos, val);
11892 }
11893
11894 /*!
11895 @brief inserts elements
11896
11897 Inserts @a cnt copies of @a val before iterator @a pos.
11898
11899 @param[in] pos iterator before which the content will be inserted; may be
11900 the end() iterator
11901 @param[in] cnt number of copies of @a val to insert
11902 @param[in] val element to insert
11903 @return iterator pointing to the first element inserted, or @a pos if
11904 `cnt==0`
11905
Ed Tanousba9f9a62017-10-11 16:40:35 -070011906 @throw type_error.309 if called on JSON values other than arrays; example:
11907 `"cannot use insert() with string"`
11908 @throw invalid_iterator.202 if @a pos is not an iterator of *this;
11909 example: `"iterator does not fit current value"`
Ed Tanous3dac7492017-08-02 13:46:20 -070011910
11911 @complexity Linear in @a cnt plus linear in the distance between @a pos
11912 and end of the container.
11913
11914 @liveexample{The example shows how `insert()` is used.,insert__count}
11915
11916 @since version 1.0.0
11917 */
11918 iterator insert(const_iterator pos, size_type cnt, const basic_json& val)
11919 {
11920 // insert only works for arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -070011921 if (JSON_LIKELY(is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -070011922 {
11923 // check if iterator pos fits to this JSON value
Ed Tanousba9f9a62017-10-11 16:40:35 -070011924 if (JSON_UNLIKELY(pos.m_object != this))
Ed Tanous3dac7492017-08-02 13:46:20 -070011925 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070011926 JSON_THROW(invalid_iterator::create(202, "iterator does not fit current value"));
Ed Tanous3dac7492017-08-02 13:46:20 -070011927 }
11928
11929 // insert to array and return iterator
11930 iterator result(this);
11931 result.m_it.array_iterator = m_value.array->insert(pos.m_it.array_iterator, cnt, val);
11932 return result;
11933 }
11934
Ed Tanousba9f9a62017-10-11 16:40:35 -070011935 JSON_THROW(type_error::create(309, "cannot use insert() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070011936 }
11937
11938 /*!
11939 @brief inserts elements
11940
11941 Inserts elements from range `[first, last)` before iterator @a pos.
11942
11943 @param[in] pos iterator before which the content will be inserted; may be
11944 the end() iterator
11945 @param[in] first begin of the range of elements to insert
11946 @param[in] last end of the range of elements to insert
11947
Ed Tanousba9f9a62017-10-11 16:40:35 -070011948 @throw type_error.309 if called on JSON values other than arrays; example:
11949 `"cannot use insert() with string"`
11950 @throw invalid_iterator.202 if @a pos is not an iterator of *this;
11951 example: `"iterator does not fit current value"`
11952 @throw invalid_iterator.210 if @a first and @a last do not belong to the
11953 same JSON value; example: `"iterators do not fit"`
11954 @throw invalid_iterator.211 if @a first or @a last are iterators into
Ed Tanous3dac7492017-08-02 13:46:20 -070011955 container for which insert is called; example: `"passed iterators may not
11956 belong to container"`
11957
11958 @return iterator pointing to the first element inserted, or @a pos if
11959 `first==last`
11960
11961 @complexity Linear in `std::distance(first, last)` plus linear in the
11962 distance between @a pos and end of the container.
11963
11964 @liveexample{The example shows how `insert()` is used.,insert__range}
11965
11966 @since version 1.0.0
11967 */
11968 iterator insert(const_iterator pos, const_iterator first, const_iterator last)
11969 {
11970 // insert only works for arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -070011971 if (JSON_UNLIKELY(not is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -070011972 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070011973 JSON_THROW(type_error::create(309, "cannot use insert() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070011974 }
11975
11976 // check if iterator pos fits to this JSON value
Ed Tanousba9f9a62017-10-11 16:40:35 -070011977 if (JSON_UNLIKELY(pos.m_object != this))
Ed Tanous3dac7492017-08-02 13:46:20 -070011978 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070011979 JSON_THROW(invalid_iterator::create(202, "iterator does not fit current value"));
Ed Tanous3dac7492017-08-02 13:46:20 -070011980 }
11981
11982 // check if range iterators belong to the same JSON object
Ed Tanousba9f9a62017-10-11 16:40:35 -070011983 if (JSON_UNLIKELY(first.m_object != last.m_object))
Ed Tanous3dac7492017-08-02 13:46:20 -070011984 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070011985 JSON_THROW(invalid_iterator::create(210, "iterators do not fit"));
Ed Tanous3dac7492017-08-02 13:46:20 -070011986 }
11987
Ed Tanousba9f9a62017-10-11 16:40:35 -070011988 if (JSON_UNLIKELY(first.m_object == this or last.m_object == this))
Ed Tanous3dac7492017-08-02 13:46:20 -070011989 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070011990 JSON_THROW(invalid_iterator::create(211, "passed iterators may not belong to container"));
Ed Tanous3dac7492017-08-02 13:46:20 -070011991 }
11992
11993 // insert to array and return iterator
11994 iterator result(this);
11995 result.m_it.array_iterator = m_value.array->insert(
11996 pos.m_it.array_iterator,
11997 first.m_it.array_iterator,
11998 last.m_it.array_iterator);
11999 return result;
12000 }
12001
12002 /*!
12003 @brief inserts elements
12004
12005 Inserts elements from initializer list @a ilist before iterator @a pos.
12006
12007 @param[in] pos iterator before which the content will be inserted; may be
12008 the end() iterator
12009 @param[in] ilist initializer list to insert the values from
12010
Ed Tanousba9f9a62017-10-11 16:40:35 -070012011 @throw type_error.309 if called on JSON values other than arrays; example:
12012 `"cannot use insert() with string"`
12013 @throw invalid_iterator.202 if @a pos is not an iterator of *this;
12014 example: `"iterator does not fit current value"`
Ed Tanous3dac7492017-08-02 13:46:20 -070012015
12016 @return iterator pointing to the first element inserted, or @a pos if
12017 `ilist` is empty
12018
12019 @complexity Linear in `ilist.size()` plus linear in the distance between
12020 @a pos and end of the container.
12021
12022 @liveexample{The example shows how `insert()` is used.,insert__ilist}
12023
12024 @since version 1.0.0
12025 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070012026 iterator insert(const_iterator pos, initializer_list_t ilist)
Ed Tanous3dac7492017-08-02 13:46:20 -070012027 {
12028 // insert only works for arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -070012029 if (JSON_UNLIKELY(not is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -070012030 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012031 JSON_THROW(type_error::create(309, "cannot use insert() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070012032 }
12033
12034 // check if iterator pos fits to this JSON value
Ed Tanousba9f9a62017-10-11 16:40:35 -070012035 if (JSON_UNLIKELY(pos.m_object != this))
Ed Tanous3dac7492017-08-02 13:46:20 -070012036 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012037 JSON_THROW(invalid_iterator::create(202, "iterator does not fit current value"));
Ed Tanous3dac7492017-08-02 13:46:20 -070012038 }
12039
12040 // insert to array and return iterator
12041 iterator result(this);
Ed Tanousba9f9a62017-10-11 16:40:35 -070012042 result.m_it.array_iterator = m_value.array->insert(pos.m_it.array_iterator, ilist.begin(), ilist.end());
Ed Tanous3dac7492017-08-02 13:46:20 -070012043 return result;
12044 }
12045
12046 /*!
Ed Tanousba9f9a62017-10-11 16:40:35 -070012047 @brief inserts elements
12048
12049 Inserts elements from range `[first, last)`.
12050
12051 @param[in] first begin of the range of elements to insert
12052 @param[in] last end of the range of elements to insert
12053
12054 @throw type_error.309 if called on JSON values other than objects; example:
12055 `"cannot use insert() with string"`
12056 @throw invalid_iterator.202 if iterator @a first or @a last does does not
12057 point to an object; example: `"iterators first and last must point to
12058 objects"`
12059 @throw invalid_iterator.210 if @a first and @a last do not belong to the
12060 same JSON value; example: `"iterators do not fit"`
12061
12062 @complexity Logarithmic: `O(N*log(size() + N))`, where `N` is the number
12063 of elements to insert.
12064
12065 @liveexample{The example shows how `insert()` is used.,insert__range_object}
12066
12067 @since version 3.0.0
12068 */
12069 void insert(const_iterator first, const_iterator last)
12070 {
12071 // insert only works for objects
12072 if (JSON_UNLIKELY(not is_object()))
12073 {
12074 JSON_THROW(type_error::create(309, "cannot use insert() with " + std::string(type_name())));
12075 }
12076
12077 // check if range iterators belong to the same JSON object
12078 if (JSON_UNLIKELY(first.m_object != last.m_object))
12079 {
12080 JSON_THROW(invalid_iterator::create(210, "iterators do not fit"));
12081 }
12082
12083 // passed iterators must belong to objects
12084 if (JSON_UNLIKELY(not first.m_object->is_object()
12085 or not last.m_object->is_object()))
12086 {
12087 JSON_THROW(invalid_iterator::create(202, "iterators first and last must point to objects"));
12088 }
12089
12090 m_value.object->insert(first.m_it.object_iterator, last.m_it.object_iterator);
12091 }
12092
12093 /*!
12094 @brief updates a JSON object from another object, overwriting existing keys
12095
12096 Inserts all values from JSON object @a j and overwrites existing keys.
12097
12098 @param[in] j JSON object to read values from
12099
12100 @throw type_error.312 if called on JSON values other than objects; example:
12101 `"cannot use update() with string"`
12102
12103 @complexity O(N*log(size() + N)), where N is the number of elements to
12104 insert.
12105
12106 @liveexample{The example shows how `update()` is used.,update}
12107
12108 @sa https://docs.python.org/3.6/library/stdtypes.html#dict.update
12109
12110 @since version 3.0.0
12111 */
12112 void update(const_reference j)
12113 {
12114 // implicitly convert null value to an empty object
12115 if (is_null())
12116 {
12117 m_type = value_t::object;
12118 m_value.object = create<object_t>();
12119 assert_invariant();
12120 }
12121
12122 if (JSON_UNLIKELY(not is_object()))
12123 {
12124 JSON_THROW(type_error::create(312, "cannot use update() with " + std::string(type_name())));
12125 }
12126 if (JSON_UNLIKELY(not j.is_object()))
12127 {
12128 JSON_THROW(type_error::create(312, "cannot use update() with " + std::string(j.type_name())));
12129 }
12130
12131 for (auto it = j.begin(); it != j.end(); ++it)
12132 {
12133 m_value.object->operator[](it.key()) = it.value();
12134 }
12135 }
12136
12137 /*!
12138 @brief updates a JSON object from another object, overwriting existing keys
12139
12140 Inserts all values from from range `[first, last)` and overwrites existing
12141 keys.
12142
12143 @param[in] first begin of the range of elements to insert
12144 @param[in] last end of the range of elements to insert
12145
12146 @throw type_error.312 if called on JSON values other than objects; example:
12147 `"cannot use update() with string"`
12148 @throw invalid_iterator.202 if iterator @a first or @a last does does not
12149 point to an object; example: `"iterators first and last must point to
12150 objects"`
12151 @throw invalid_iterator.210 if @a first and @a last do not belong to the
12152 same JSON value; example: `"iterators do not fit"`
12153
12154 @complexity O(N*log(size() + N)), where N is the number of elements to
12155 insert.
12156
12157 @liveexample{The example shows how `update()` is used__range.,update}
12158
12159 @sa https://docs.python.org/3.6/library/stdtypes.html#dict.update
12160
12161 @since version 3.0.0
12162 */
12163 void update(const_iterator first, const_iterator last)
12164 {
12165 // implicitly convert null value to an empty object
12166 if (is_null())
12167 {
12168 m_type = value_t::object;
12169 m_value.object = create<object_t>();
12170 assert_invariant();
12171 }
12172
12173 if (JSON_UNLIKELY(not is_object()))
12174 {
12175 JSON_THROW(type_error::create(312, "cannot use update() with " + std::string(type_name())));
12176 }
12177
12178 // check if range iterators belong to the same JSON object
12179 if (JSON_UNLIKELY(first.m_object != last.m_object))
12180 {
12181 JSON_THROW(invalid_iterator::create(210, "iterators do not fit"));
12182 }
12183
12184 // passed iterators must belong to objects
12185 if (JSON_UNLIKELY(not first.m_object->is_object()
12186 or not first.m_object->is_object()))
12187 {
12188 JSON_THROW(invalid_iterator::create(202, "iterators first and last must point to objects"));
12189 }
12190
12191 for (auto it = first; it != last; ++it)
12192 {
12193 m_value.object->operator[](it.key()) = it.value();
12194 }
12195 }
12196
12197 /*!
Ed Tanous3dac7492017-08-02 13:46:20 -070012198 @brief exchanges the values
12199
12200 Exchanges the contents of the JSON value with those of @a other. Does not
12201 invoke any move, copy, or swap operations on individual elements. All
12202 iterators and references remain valid. The past-the-end iterator is
12203 invalidated.
12204
12205 @param[in,out] other JSON value to exchange the contents with
12206
12207 @complexity Constant.
12208
12209 @liveexample{The example below shows how JSON values can be swapped with
12210 `swap()`.,swap__reference}
12211
12212 @since version 1.0.0
12213 */
12214 void swap(reference other) noexcept (
12215 std::is_nothrow_move_constructible<value_t>::value and
12216 std::is_nothrow_move_assignable<value_t>::value and
12217 std::is_nothrow_move_constructible<json_value>::value and
12218 std::is_nothrow_move_assignable<json_value>::value
12219 )
12220 {
12221 std::swap(m_type, other.m_type);
12222 std::swap(m_value, other.m_value);
12223 assert_invariant();
12224 }
12225
12226 /*!
12227 @brief exchanges the values
12228
12229 Exchanges the contents of a JSON array with those of @a other. Does not
12230 invoke any move, copy, or swap operations on individual elements. All
12231 iterators and references remain valid. The past-the-end iterator is
12232 invalidated.
12233
12234 @param[in,out] other array to exchange the contents with
12235
Ed Tanousba9f9a62017-10-11 16:40:35 -070012236 @throw type_error.310 when JSON value is not an array; example: `"cannot
12237 use swap() with string"`
Ed Tanous3dac7492017-08-02 13:46:20 -070012238
12239 @complexity Constant.
12240
12241 @liveexample{The example below shows how arrays can be swapped with
12242 `swap()`.,swap__array_t}
12243
12244 @since version 1.0.0
12245 */
12246 void swap(array_t& other)
12247 {
12248 // swap only works for arrays
Ed Tanousba9f9a62017-10-11 16:40:35 -070012249 if (JSON_LIKELY(is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -070012250 {
12251 std::swap(*(m_value.array), other);
12252 }
12253 else
12254 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012255 JSON_THROW(type_error::create(310, "cannot use swap() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070012256 }
12257 }
12258
12259 /*!
12260 @brief exchanges the values
12261
12262 Exchanges the contents of a JSON object with those of @a other. Does not
12263 invoke any move, copy, or swap operations on individual elements. All
12264 iterators and references remain valid. The past-the-end iterator is
12265 invalidated.
12266
12267 @param[in,out] other object to exchange the contents with
12268
Ed Tanousba9f9a62017-10-11 16:40:35 -070012269 @throw type_error.310 when JSON value is not an object; example:
Ed Tanous3dac7492017-08-02 13:46:20 -070012270 `"cannot use swap() with string"`
12271
12272 @complexity Constant.
12273
12274 @liveexample{The example below shows how objects can be swapped with
12275 `swap()`.,swap__object_t}
12276
12277 @since version 1.0.0
12278 */
12279 void swap(object_t& other)
12280 {
12281 // swap only works for objects
Ed Tanousba9f9a62017-10-11 16:40:35 -070012282 if (JSON_LIKELY(is_object()))
Ed Tanous3dac7492017-08-02 13:46:20 -070012283 {
12284 std::swap(*(m_value.object), other);
12285 }
12286 else
12287 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012288 JSON_THROW(type_error::create(310, "cannot use swap() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070012289 }
12290 }
12291
12292 /*!
12293 @brief exchanges the values
12294
12295 Exchanges the contents of a JSON string with those of @a other. Does not
12296 invoke any move, copy, or swap operations on individual elements. All
12297 iterators and references remain valid. The past-the-end iterator is
12298 invalidated.
12299
12300 @param[in,out] other string to exchange the contents with
12301
Ed Tanousba9f9a62017-10-11 16:40:35 -070012302 @throw type_error.310 when JSON value is not a string; example: `"cannot
Ed Tanous3dac7492017-08-02 13:46:20 -070012303 use swap() with boolean"`
12304
12305 @complexity Constant.
12306
12307 @liveexample{The example below shows how strings can be swapped with
12308 `swap()`.,swap__string_t}
12309
12310 @since version 1.0.0
12311 */
12312 void swap(string_t& other)
12313 {
12314 // swap only works for strings
Ed Tanousba9f9a62017-10-11 16:40:35 -070012315 if (JSON_LIKELY(is_string()))
Ed Tanous3dac7492017-08-02 13:46:20 -070012316 {
12317 std::swap(*(m_value.string), other);
12318 }
12319 else
12320 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012321 JSON_THROW(type_error::create(310, "cannot use swap() with " + std::string(type_name())));
Ed Tanous3dac7492017-08-02 13:46:20 -070012322 }
12323 }
12324
12325 /// @}
12326
12327 public:
12328 //////////////////////////////////////////
12329 // lexicographical comparison operators //
12330 //////////////////////////////////////////
12331
12332 /// @name lexicographical comparison operators
12333 /// @{
12334
12335 /*!
12336 @brief comparison: equal
12337
12338 Compares two JSON values for equality according to the following rules:
12339 - Two JSON values are equal if (1) they are from the same type and (2)
Ed Tanousba9f9a62017-10-11 16:40:35 -070012340 their stored values are the same according to their respective
12341 `operator==`.
Ed Tanous3dac7492017-08-02 13:46:20 -070012342 - Integer and floating-point numbers are automatically converted before
Ed Tanousba9f9a62017-10-11 16:40:35 -070012343 comparison. Note than two NaN values are always treated as unequal.
Ed Tanous3dac7492017-08-02 13:46:20 -070012344 - Two JSON null values are equal.
12345
Ed Tanousba9f9a62017-10-11 16:40:35 -070012346 @note Floating-point inside JSON values numbers are compared with
12347 `json::number_float_t::operator==` which is `double::operator==` by
12348 default. To compare floating-point while respecting an epsilon, an alternative
12349 [comparison function](https://github.com/mariokonrad/marnav/blob/master/src/marnav/math/floatingpoint.hpp#L34-#L39)
12350 could be used, for instance
12351 @code {.cpp}
12352 template <typename T, typename = typename std::enable_if<std::is_floating_point<T>::value, T>::type>
12353 inline bool is_same(T a, T b, T epsilon = std::numeric_limits<T>::epsilon()) noexcept
12354 {
12355 return std::abs(a - b) <= epsilon;
12356 }
12357 @endcode
12358
12359 @note NaN values never compare equal to themselves or to other NaN values.
12360
Ed Tanous3dac7492017-08-02 13:46:20 -070012361 @param[in] lhs first JSON value to consider
12362 @param[in] rhs second JSON value to consider
12363 @return whether the values @a lhs and @a rhs are equal
12364
Ed Tanousba9f9a62017-10-11 16:40:35 -070012365 @exceptionsafety No-throw guarantee: this function never throws exceptions.
12366
Ed Tanous3dac7492017-08-02 13:46:20 -070012367 @complexity Linear.
12368
12369 @liveexample{The example demonstrates comparing several JSON
12370 types.,operator__equal}
12371
12372 @since version 1.0.0
12373 */
12374 friend bool operator==(const_reference lhs, const_reference rhs) noexcept
12375 {
12376 const auto lhs_type = lhs.type();
12377 const auto rhs_type = rhs.type();
12378
12379 if (lhs_type == rhs_type)
12380 {
12381 switch (lhs_type)
12382 {
12383 case value_t::array:
Ed Tanousba9f9a62017-10-11 16:40:35 -070012384 return (*lhs.m_value.array == *rhs.m_value.array);
12385
Ed Tanous3dac7492017-08-02 13:46:20 -070012386 case value_t::object:
Ed Tanousba9f9a62017-10-11 16:40:35 -070012387 return (*lhs.m_value.object == *rhs.m_value.object);
12388
Ed Tanous3dac7492017-08-02 13:46:20 -070012389 case value_t::null:
Ed Tanous3dac7492017-08-02 13:46:20 -070012390 return true;
Ed Tanousba9f9a62017-10-11 16:40:35 -070012391
Ed Tanous3dac7492017-08-02 13:46:20 -070012392 case value_t::string:
Ed Tanousba9f9a62017-10-11 16:40:35 -070012393 return (*lhs.m_value.string == *rhs.m_value.string);
12394
Ed Tanous3dac7492017-08-02 13:46:20 -070012395 case value_t::boolean:
Ed Tanousba9f9a62017-10-11 16:40:35 -070012396 return (lhs.m_value.boolean == rhs.m_value.boolean);
12397
Ed Tanous3dac7492017-08-02 13:46:20 -070012398 case value_t::number_integer:
Ed Tanousba9f9a62017-10-11 16:40:35 -070012399 return (lhs.m_value.number_integer == rhs.m_value.number_integer);
12400
Ed Tanous3dac7492017-08-02 13:46:20 -070012401 case value_t::number_unsigned:
Ed Tanousba9f9a62017-10-11 16:40:35 -070012402 return (lhs.m_value.number_unsigned == rhs.m_value.number_unsigned);
12403
Ed Tanous3dac7492017-08-02 13:46:20 -070012404 case value_t::number_float:
Ed Tanousba9f9a62017-10-11 16:40:35 -070012405 return (lhs.m_value.number_float == rhs.m_value.number_float);
12406
Ed Tanous3dac7492017-08-02 13:46:20 -070012407 default:
Ed Tanous3dac7492017-08-02 13:46:20 -070012408 return false;
Ed Tanous3dac7492017-08-02 13:46:20 -070012409 }
12410 }
12411 else if (lhs_type == value_t::number_integer and rhs_type == value_t::number_float)
12412 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012413 return (static_cast<number_float_t>(lhs.m_value.number_integer) == rhs.m_value.number_float);
Ed Tanous3dac7492017-08-02 13:46:20 -070012414 }
12415 else if (lhs_type == value_t::number_float and rhs_type == value_t::number_integer)
12416 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012417 return (lhs.m_value.number_float == static_cast<number_float_t>(rhs.m_value.number_integer));
Ed Tanous3dac7492017-08-02 13:46:20 -070012418 }
12419 else if (lhs_type == value_t::number_unsigned and rhs_type == value_t::number_float)
12420 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012421 return (static_cast<number_float_t>(lhs.m_value.number_unsigned) == rhs.m_value.number_float);
Ed Tanous3dac7492017-08-02 13:46:20 -070012422 }
12423 else if (lhs_type == value_t::number_float and rhs_type == value_t::number_unsigned)
12424 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012425 return (lhs.m_value.number_float == static_cast<number_float_t>(rhs.m_value.number_unsigned));
Ed Tanous3dac7492017-08-02 13:46:20 -070012426 }
12427 else if (lhs_type == value_t::number_unsigned and rhs_type == value_t::number_integer)
12428 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012429 return (static_cast<number_integer_t>(lhs.m_value.number_unsigned) == rhs.m_value.number_integer);
Ed Tanous3dac7492017-08-02 13:46:20 -070012430 }
12431 else if (lhs_type == value_t::number_integer and rhs_type == value_t::number_unsigned)
12432 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012433 return (lhs.m_value.number_integer == static_cast<number_integer_t>(rhs.m_value.number_unsigned));
Ed Tanous3dac7492017-08-02 13:46:20 -070012434 }
12435
12436 return false;
12437 }
12438
12439 /*!
12440 @brief comparison: equal
12441 @copydoc operator==(const_reference, const_reference)
12442 */
12443 template<typename ScalarType, typename std::enable_if<
12444 std::is_scalar<ScalarType>::value, int>::type = 0>
12445 friend bool operator==(const_reference lhs, const ScalarType rhs) noexcept
12446 {
12447 return (lhs == basic_json(rhs));
12448 }
12449
12450 /*!
12451 @brief comparison: equal
12452 @copydoc operator==(const_reference, const_reference)
12453 */
12454 template<typename ScalarType, typename std::enable_if<
12455 std::is_scalar<ScalarType>::value, int>::type = 0>
12456 friend bool operator==(const ScalarType lhs, const_reference rhs) noexcept
12457 {
12458 return (basic_json(lhs) == rhs);
12459 }
12460
12461 /*!
12462 @brief comparison: not equal
12463
12464 Compares two JSON values for inequality by calculating `not (lhs == rhs)`.
12465
12466 @param[in] lhs first JSON value to consider
12467 @param[in] rhs second JSON value to consider
12468 @return whether the values @a lhs and @a rhs are not equal
12469
12470 @complexity Linear.
12471
Ed Tanousba9f9a62017-10-11 16:40:35 -070012472 @exceptionsafety No-throw guarantee: this function never throws exceptions.
12473
Ed Tanous3dac7492017-08-02 13:46:20 -070012474 @liveexample{The example demonstrates comparing several JSON
12475 types.,operator__notequal}
12476
12477 @since version 1.0.0
12478 */
12479 friend bool operator!=(const_reference lhs, const_reference rhs) noexcept
12480 {
12481 return not (lhs == rhs);
12482 }
12483
12484 /*!
12485 @brief comparison: not equal
12486 @copydoc operator!=(const_reference, const_reference)
12487 */
12488 template<typename ScalarType, typename std::enable_if<
12489 std::is_scalar<ScalarType>::value, int>::type = 0>
12490 friend bool operator!=(const_reference lhs, const ScalarType rhs) noexcept
12491 {
12492 return (lhs != basic_json(rhs));
12493 }
12494
12495 /*!
12496 @brief comparison: not equal
12497 @copydoc operator!=(const_reference, const_reference)
12498 */
12499 template<typename ScalarType, typename std::enable_if<
12500 std::is_scalar<ScalarType>::value, int>::type = 0>
12501 friend bool operator!=(const ScalarType lhs, const_reference rhs) noexcept
12502 {
12503 return (basic_json(lhs) != rhs);
12504 }
12505
12506 /*!
12507 @brief comparison: less than
12508
12509 Compares whether one JSON value @a lhs is less than another JSON value @a
12510 rhs according to the following rules:
12511 - If @a lhs and @a rhs have the same type, the values are compared using
12512 the default `<` operator.
12513 - Integer and floating-point numbers are automatically converted before
12514 comparison
12515 - In case @a lhs and @a rhs have different types, the values are ignored
12516 and the order of the types is considered, see
12517 @ref operator<(const value_t, const value_t).
12518
12519 @param[in] lhs first JSON value to consider
12520 @param[in] rhs second JSON value to consider
12521 @return whether @a lhs is less than @a rhs
12522
12523 @complexity Linear.
12524
Ed Tanousba9f9a62017-10-11 16:40:35 -070012525 @exceptionsafety No-throw guarantee: this function never throws exceptions.
12526
Ed Tanous3dac7492017-08-02 13:46:20 -070012527 @liveexample{The example demonstrates comparing several JSON
12528 types.,operator__less}
12529
12530 @since version 1.0.0
12531 */
12532 friend bool operator<(const_reference lhs, const_reference rhs) noexcept
12533 {
12534 const auto lhs_type = lhs.type();
12535 const auto rhs_type = rhs.type();
12536
12537 if (lhs_type == rhs_type)
12538 {
12539 switch (lhs_type)
12540 {
12541 case value_t::array:
Ed Tanousba9f9a62017-10-11 16:40:35 -070012542 return (*lhs.m_value.array) < (*rhs.m_value.array);
12543
Ed Tanous3dac7492017-08-02 13:46:20 -070012544 case value_t::object:
Ed Tanous3dac7492017-08-02 13:46:20 -070012545 return *lhs.m_value.object < *rhs.m_value.object;
Ed Tanousba9f9a62017-10-11 16:40:35 -070012546
Ed Tanous3dac7492017-08-02 13:46:20 -070012547 case value_t::null:
Ed Tanous3dac7492017-08-02 13:46:20 -070012548 return false;
Ed Tanousba9f9a62017-10-11 16:40:35 -070012549
Ed Tanous3dac7492017-08-02 13:46:20 -070012550 case value_t::string:
Ed Tanous3dac7492017-08-02 13:46:20 -070012551 return *lhs.m_value.string < *rhs.m_value.string;
Ed Tanousba9f9a62017-10-11 16:40:35 -070012552
Ed Tanous3dac7492017-08-02 13:46:20 -070012553 case value_t::boolean:
Ed Tanous3dac7492017-08-02 13:46:20 -070012554 return lhs.m_value.boolean < rhs.m_value.boolean;
Ed Tanousba9f9a62017-10-11 16:40:35 -070012555
Ed Tanous3dac7492017-08-02 13:46:20 -070012556 case value_t::number_integer:
Ed Tanous3dac7492017-08-02 13:46:20 -070012557 return lhs.m_value.number_integer < rhs.m_value.number_integer;
Ed Tanousba9f9a62017-10-11 16:40:35 -070012558
Ed Tanous3dac7492017-08-02 13:46:20 -070012559 case value_t::number_unsigned:
Ed Tanous3dac7492017-08-02 13:46:20 -070012560 return lhs.m_value.number_unsigned < rhs.m_value.number_unsigned;
Ed Tanousba9f9a62017-10-11 16:40:35 -070012561
Ed Tanous3dac7492017-08-02 13:46:20 -070012562 case value_t::number_float:
Ed Tanous3dac7492017-08-02 13:46:20 -070012563 return lhs.m_value.number_float < rhs.m_value.number_float;
Ed Tanousba9f9a62017-10-11 16:40:35 -070012564
Ed Tanous3dac7492017-08-02 13:46:20 -070012565 default:
Ed Tanous3dac7492017-08-02 13:46:20 -070012566 return false;
Ed Tanous3dac7492017-08-02 13:46:20 -070012567 }
12568 }
12569 else if (lhs_type == value_t::number_integer and rhs_type == value_t::number_float)
12570 {
12571 return static_cast<number_float_t>(lhs.m_value.number_integer) < rhs.m_value.number_float;
12572 }
12573 else if (lhs_type == value_t::number_float and rhs_type == value_t::number_integer)
12574 {
12575 return lhs.m_value.number_float < static_cast<number_float_t>(rhs.m_value.number_integer);
12576 }
12577 else if (lhs_type == value_t::number_unsigned and rhs_type == value_t::number_float)
12578 {
12579 return static_cast<number_float_t>(lhs.m_value.number_unsigned) < rhs.m_value.number_float;
12580 }
12581 else if (lhs_type == value_t::number_float and rhs_type == value_t::number_unsigned)
12582 {
12583 return lhs.m_value.number_float < static_cast<number_float_t>(rhs.m_value.number_unsigned);
12584 }
12585 else if (lhs_type == value_t::number_integer and rhs_type == value_t::number_unsigned)
12586 {
12587 return lhs.m_value.number_integer < static_cast<number_integer_t>(rhs.m_value.number_unsigned);
12588 }
12589 else if (lhs_type == value_t::number_unsigned and rhs_type == value_t::number_integer)
12590 {
12591 return static_cast<number_integer_t>(lhs.m_value.number_unsigned) < rhs.m_value.number_integer;
12592 }
12593
12594 // We only reach this line if we cannot compare values. In that case,
12595 // we compare types. Note we have to call the operator explicitly,
12596 // because MSVC has problems otherwise.
12597 return operator<(lhs_type, rhs_type);
12598 }
12599
12600 /*!
Ed Tanousba9f9a62017-10-11 16:40:35 -070012601 @brief comparison: less than
12602 @copydoc operator<(const_reference, const_reference)
12603 */
12604 template<typename ScalarType, typename std::enable_if<
12605 std::is_scalar<ScalarType>::value, int>::type = 0>
12606 friend bool operator<(const_reference lhs, const ScalarType rhs) noexcept
12607 {
12608 return (lhs < basic_json(rhs));
12609 }
12610
12611 /*!
12612 @brief comparison: less than
12613 @copydoc operator<(const_reference, const_reference)
12614 */
12615 template<typename ScalarType, typename std::enable_if<
12616 std::is_scalar<ScalarType>::value, int>::type = 0>
12617 friend bool operator<(const ScalarType lhs, const_reference rhs) noexcept
12618 {
12619 return (basic_json(lhs) < rhs);
12620 }
12621
12622 /*!
Ed Tanous3dac7492017-08-02 13:46:20 -070012623 @brief comparison: less than or equal
12624
12625 Compares whether one JSON value @a lhs is less than or equal to another
12626 JSON value by calculating `not (rhs < lhs)`.
12627
12628 @param[in] lhs first JSON value to consider
12629 @param[in] rhs second JSON value to consider
12630 @return whether @a lhs is less than or equal to @a rhs
12631
12632 @complexity Linear.
12633
Ed Tanousba9f9a62017-10-11 16:40:35 -070012634 @exceptionsafety No-throw guarantee: this function never throws exceptions.
12635
Ed Tanous3dac7492017-08-02 13:46:20 -070012636 @liveexample{The example demonstrates comparing several JSON
12637 types.,operator__greater}
12638
12639 @since version 1.0.0
12640 */
12641 friend bool operator<=(const_reference lhs, const_reference rhs) noexcept
12642 {
12643 return not (rhs < lhs);
12644 }
12645
12646 /*!
Ed Tanousba9f9a62017-10-11 16:40:35 -070012647 @brief comparison: less than or equal
12648 @copydoc operator<=(const_reference, const_reference)
12649 */
12650 template<typename ScalarType, typename std::enable_if<
12651 std::is_scalar<ScalarType>::value, int>::type = 0>
12652 friend bool operator<=(const_reference lhs, const ScalarType rhs) noexcept
12653 {
12654 return (lhs <= basic_json(rhs));
12655 }
12656
12657 /*!
12658 @brief comparison: less than or equal
12659 @copydoc operator<=(const_reference, const_reference)
12660 */
12661 template<typename ScalarType, typename std::enable_if<
12662 std::is_scalar<ScalarType>::value, int>::type = 0>
12663 friend bool operator<=(const ScalarType lhs, const_reference rhs) noexcept
12664 {
12665 return (basic_json(lhs) <= rhs);
12666 }
12667
12668 /*!
Ed Tanous3dac7492017-08-02 13:46:20 -070012669 @brief comparison: greater than
12670
12671 Compares whether one JSON value @a lhs is greater than another
12672 JSON value by calculating `not (lhs <= rhs)`.
12673
12674 @param[in] lhs first JSON value to consider
12675 @param[in] rhs second JSON value to consider
12676 @return whether @a lhs is greater than to @a rhs
12677
12678 @complexity Linear.
12679
Ed Tanousba9f9a62017-10-11 16:40:35 -070012680 @exceptionsafety No-throw guarantee: this function never throws exceptions.
12681
Ed Tanous3dac7492017-08-02 13:46:20 -070012682 @liveexample{The example demonstrates comparing several JSON
12683 types.,operator__lessequal}
12684
12685 @since version 1.0.0
12686 */
12687 friend bool operator>(const_reference lhs, const_reference rhs) noexcept
12688 {
12689 return not (lhs <= rhs);
12690 }
12691
12692 /*!
Ed Tanousba9f9a62017-10-11 16:40:35 -070012693 @brief comparison: greater than
12694 @copydoc operator>(const_reference, const_reference)
12695 */
12696 template<typename ScalarType, typename std::enable_if<
12697 std::is_scalar<ScalarType>::value, int>::type = 0>
12698 friend bool operator>(const_reference lhs, const ScalarType rhs) noexcept
12699 {
12700 return (lhs > basic_json(rhs));
12701 }
12702
12703 /*!
12704 @brief comparison: greater than
12705 @copydoc operator>(const_reference, const_reference)
12706 */
12707 template<typename ScalarType, typename std::enable_if<
12708 std::is_scalar<ScalarType>::value, int>::type = 0>
12709 friend bool operator>(const ScalarType lhs, const_reference rhs) noexcept
12710 {
12711 return (basic_json(lhs) > rhs);
12712 }
12713
12714 /*!
Ed Tanous3dac7492017-08-02 13:46:20 -070012715 @brief comparison: greater than or equal
12716
12717 Compares whether one JSON value @a lhs is greater than or equal to another
12718 JSON value by calculating `not (lhs < rhs)`.
12719
12720 @param[in] lhs first JSON value to consider
12721 @param[in] rhs second JSON value to consider
12722 @return whether @a lhs is greater than or equal to @a rhs
12723
12724 @complexity Linear.
12725
Ed Tanousba9f9a62017-10-11 16:40:35 -070012726 @exceptionsafety No-throw guarantee: this function never throws exceptions.
12727
Ed Tanous3dac7492017-08-02 13:46:20 -070012728 @liveexample{The example demonstrates comparing several JSON
12729 types.,operator__greaterequal}
12730
12731 @since version 1.0.0
12732 */
12733 friend bool operator>=(const_reference lhs, const_reference rhs) noexcept
12734 {
12735 return not (lhs < rhs);
12736 }
12737
Ed Tanousba9f9a62017-10-11 16:40:35 -070012738 /*!
12739 @brief comparison: greater than or equal
12740 @copydoc operator>=(const_reference, const_reference)
12741 */
12742 template<typename ScalarType, typename std::enable_if<
12743 std::is_scalar<ScalarType>::value, int>::type = 0>
12744 friend bool operator>=(const_reference lhs, const ScalarType rhs) noexcept
12745 {
12746 return (lhs >= basic_json(rhs));
12747 }
Ed Tanous3dac7492017-08-02 13:46:20 -070012748
Ed Tanousba9f9a62017-10-11 16:40:35 -070012749 /*!
12750 @brief comparison: greater than or equal
12751 @copydoc operator>=(const_reference, const_reference)
12752 */
12753 template<typename ScalarType, typename std::enable_if<
12754 std::is_scalar<ScalarType>::value, int>::type = 0>
12755 friend bool operator>=(const ScalarType lhs, const_reference rhs) noexcept
12756 {
12757 return (basic_json(lhs) >= rhs);
12758 }
12759
12760 /// @}
Ed Tanous3dac7492017-08-02 13:46:20 -070012761
12762 ///////////////////
12763 // serialization //
12764 ///////////////////
12765
12766 /// @name serialization
12767 /// @{
12768
12769 /*!
12770 @brief serialize to stream
12771
12772 Serialize the given JSON value @a j to the output stream @a o. The JSON
Ed Tanousba9f9a62017-10-11 16:40:35 -070012773 value will be serialized using the @ref dump member function.
12774
12775 - The indentation of the output can be controlled with the member variable
12776 `width` of the output stream @a o. For instance, using the manipulator
12777 `std::setw(4)` on @a o sets the indentation level to `4` and the
12778 serialization result is the same as calling `dump(4)`.
12779
12780 - The indentation characrer can be controlled with the member variable
12781 `fill` of the output stream @a o. For instance, the manipulator
12782 `std::setfill('\\t')` sets indentation to use a tab character rather than
12783 the default space character.
Ed Tanous3dac7492017-08-02 13:46:20 -070012784
12785 @param[in,out] o stream to serialize to
12786 @param[in] j JSON value to serialize
12787
12788 @return the stream @a o
12789
12790 @complexity Linear.
12791
12792 @liveexample{The example below shows the serialization with different
12793 parameters to `width` to adjust the indentation level.,operator_serialize}
12794
Ed Tanousba9f9a62017-10-11 16:40:35 -070012795 @since version 1.0.0; indentaction character added in version 3.0.0
Ed Tanous3dac7492017-08-02 13:46:20 -070012796 */
12797 friend std::ostream& operator<<(std::ostream& o, const basic_json& j)
12798 {
12799 // read width member and use it as indentation parameter if nonzero
12800 const bool pretty_print = (o.width() > 0);
12801 const auto indentation = (pretty_print ? o.width() : 0);
12802
12803 // reset width to 0 for subsequent calls to this stream
12804 o.width(0);
12805
12806 // do the actual serialization
Ed Tanousba9f9a62017-10-11 16:40:35 -070012807 serializer s(detail::output_adapter<char>(o), o.fill());
12808 s.dump(j, pretty_print, false, static_cast<unsigned int>(indentation));
Ed Tanous3dac7492017-08-02 13:46:20 -070012809 return o;
12810 }
12811
12812 /*!
12813 @brief serialize to stream
Ed Tanousba9f9a62017-10-11 16:40:35 -070012814 @deprecated This stream operator is deprecated and will be removed in a
12815 future version of the library. Please use
12816 @ref operator<<(std::ostream&, const basic_json&)
12817 instead; that is, replace calls like `j >> o;` with `o << j;`.
12818 @since version 1.0.0; deprecated since version 3.0.0
Ed Tanous3dac7492017-08-02 13:46:20 -070012819 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070012820 JSON_DEPRECATED
Ed Tanous3dac7492017-08-02 13:46:20 -070012821 friend std::ostream& operator>>(const basic_json& j, std::ostream& o)
12822 {
12823 return o << j;
12824 }
12825
12826 /// @}
12827
12828
12829 /////////////////////
12830 // deserialization //
12831 /////////////////////
12832
12833 /// @name deserialization
12834 /// @{
12835
12836 /*!
Ed Tanousba9f9a62017-10-11 16:40:35 -070012837 @brief deserialize from a compatible input
Ed Tanous3dac7492017-08-02 13:46:20 -070012838
Ed Tanousba9f9a62017-10-11 16:40:35 -070012839 This function reads from a compatible input. Examples are:
12840 - an array of 1-byte values
12841 - strings with character/literal type with size of 1 byte
12842 - input streams
12843 - container with contiguous storage of 1-byte values. Compatible container
12844 types include `std::vector`, `std::string`, `std::array`,
12845 `std::valarray`, and `std::initializer_list`. Furthermore, C-style
12846 arrays can be used with `std::begin()`/`std::end()`. User-defined
12847 containers can be used as long as they implement random-access iterators
12848 and a contiguous storage.
Ed Tanous3dac7492017-08-02 13:46:20 -070012849
12850 @pre Each element of the container has a size of 1 byte. Violating this
12851 precondition yields undefined behavior. **This precondition is enforced
12852 with a static assertion.**
12853
Ed Tanousba9f9a62017-10-11 16:40:35 -070012854 @pre The container storage is contiguous. Violating this precondition
12855 yields undefined behavior. **This precondition is enforced with an
12856 assertion.**
12857 @pre Each element of the container has a size of 1 byte. Violating this
12858 precondition yields undefined behavior. **This precondition is enforced
12859 with a static assertion.**
12860
12861 @warning There is no way to enforce all preconditions at compile-time. If
12862 the function is called with a noncompliant container and with
12863 assertions switched off, the behavior is undefined and will most
12864 likely yield segmentation violation.
12865
12866 @param[in] i input to read from
Ed Tanous3dac7492017-08-02 13:46:20 -070012867 @param[in] cb a parser callback function of type @ref parser_callback_t
12868 which is used to control the deserialization by filtering unwanted values
12869 (optional)
12870
12871 @return result of the deserialization
12872
Ed Tanousba9f9a62017-10-11 16:40:35 -070012873 @throw parse_error.101 if a parse error occurs; example: `""unexpected end
12874 of input; expected string literal""`
12875 @throw parse_error.102 if to_unicode fails or surrogate error
12876 @throw parse_error.103 if to_unicode fails
12877
Ed Tanous3dac7492017-08-02 13:46:20 -070012878 @complexity Linear in the length of the input. The parser is a predictive
12879 LL(1) parser. The complexity can be higher if the parser callback function
12880 @a cb has a super-linear complexity.
12881
12882 @note A UTF-8 byte order mark is silently ignored.
12883
12884 @liveexample{The example below demonstrates the `parse()` function reading
12885 from an array.,parse__array__parser_callback_t}
12886
Ed Tanous3dac7492017-08-02 13:46:20 -070012887 @liveexample{The example below demonstrates the `parse()` function with
12888 and without callback function.,parse__string__parser_callback_t}
12889
Ed Tanous3dac7492017-08-02 13:46:20 -070012890 @liveexample{The example below demonstrates the `parse()` function with
12891 and without callback function.,parse__istream__parser_callback_t}
12892
Ed Tanousba9f9a62017-10-11 16:40:35 -070012893 @liveexample{The example below demonstrates the `parse()` function reading
12894 from a contiguous container.,parse__contiguouscontainer__parser_callback_t}
Ed Tanous3dac7492017-08-02 13:46:20 -070012895
Ed Tanousba9f9a62017-10-11 16:40:35 -070012896 @since version 2.0.3 (contiguous containers)
Ed Tanous3dac7492017-08-02 13:46:20 -070012897 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070012898 static basic_json parse(detail::input_adapter i,
12899 const parser_callback_t cb = nullptr,
12900 const bool allow_exceptions = true)
Ed Tanous3dac7492017-08-02 13:46:20 -070012901 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012902 basic_json result;
12903 parser(i, cb, allow_exceptions).parse(true, result);
12904 return result;
Ed Tanous3dac7492017-08-02 13:46:20 -070012905 }
12906
12907 /*!
Ed Tanousba9f9a62017-10-11 16:40:35 -070012908 @copydoc basic_json parse(detail::input_adapter, const parser_callback_t)
Ed Tanous3dac7492017-08-02 13:46:20 -070012909 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070012910 static basic_json parse(detail::input_adapter& i,
12911 const parser_callback_t cb = nullptr,
12912 const bool allow_exceptions = true)
Ed Tanous3dac7492017-08-02 13:46:20 -070012913 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012914 basic_json result;
12915 parser(i, cb, allow_exceptions).parse(true, result);
12916 return result;
12917 }
12918
12919 static bool accept(detail::input_adapter i)
12920 {
12921 return parser(i).accept(true);
12922 }
12923
12924 static bool accept(detail::input_adapter& i)
12925 {
12926 return parser(i).accept(true);
Ed Tanous3dac7492017-08-02 13:46:20 -070012927 }
12928
12929 /*!
12930 @brief deserialize from an iterator range with contiguous storage
12931
12932 This function reads from an iterator range of a container with contiguous
12933 storage of 1-byte values. Compatible container types include
12934 `std::vector`, `std::string`, `std::array`, `std::valarray`, and
12935 `std::initializer_list`. Furthermore, C-style arrays can be used with
12936 `std::begin()`/`std::end()`. User-defined containers can be used as long
12937 as they implement random-access iterators and a contiguous storage.
12938
12939 @pre The iterator range is contiguous. Violating this precondition yields
12940 undefined behavior. **This precondition is enforced with an assertion.**
12941 @pre Each element in the range has a size of 1 byte. Violating this
12942 precondition yields undefined behavior. **This precondition is enforced
12943 with a static assertion.**
12944
12945 @warning There is no way to enforce all preconditions at compile-time. If
12946 the function is called with noncompliant iterators and with
12947 assertions switched off, the behavior is undefined and will most
12948 likely yield segmentation violation.
12949
12950 @tparam IteratorType iterator of container with contiguous storage
12951 @param[in] first begin of the range to parse (included)
12952 @param[in] last end of the range to parse (excluded)
12953 @param[in] cb a parser callback function of type @ref parser_callback_t
12954 which is used to control the deserialization by filtering unwanted values
12955 (optional)
12956
12957 @return result of the deserialization
12958
Ed Tanousba9f9a62017-10-11 16:40:35 -070012959 @throw parse_error.101 in case of an unexpected token
12960 @throw parse_error.102 if to_unicode fails or surrogate error
12961 @throw parse_error.103 if to_unicode fails
12962
Ed Tanous3dac7492017-08-02 13:46:20 -070012963 @complexity Linear in the length of the input. The parser is a predictive
12964 LL(1) parser. The complexity can be higher if the parser callback function
12965 @a cb has a super-linear complexity.
12966
12967 @note A UTF-8 byte order mark is silently ignored.
12968
12969 @liveexample{The example below demonstrates the `parse()` function reading
12970 from an iterator range.,parse__iteratortype__parser_callback_t}
12971
12972 @since version 2.0.3
12973 */
12974 template<class IteratorType, typename std::enable_if<
12975 std::is_base_of<
12976 std::random_access_iterator_tag,
12977 typename std::iterator_traits<IteratorType>::iterator_category>::value, int>::type = 0>
12978 static basic_json parse(IteratorType first, IteratorType last,
Ed Tanousba9f9a62017-10-11 16:40:35 -070012979 const parser_callback_t cb = nullptr,
12980 const bool allow_exceptions = true)
Ed Tanous3dac7492017-08-02 13:46:20 -070012981 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070012982 basic_json result;
12983 parser(detail::input_adapter(first, last), cb, allow_exceptions).parse(true, result);
12984 return result;
12985 }
Ed Tanous3dac7492017-08-02 13:46:20 -070012986
Ed Tanousba9f9a62017-10-11 16:40:35 -070012987 template<class IteratorType, typename std::enable_if<
12988 std::is_base_of<
12989 std::random_access_iterator_tag,
12990 typename std::iterator_traits<IteratorType>::iterator_category>::value, int>::type = 0>
12991 static bool accept(IteratorType first, IteratorType last)
12992 {
12993 return parser(detail::input_adapter(first, last)).accept(true);
Ed Tanous3dac7492017-08-02 13:46:20 -070012994 }
12995
12996 /*!
Ed Tanousba9f9a62017-10-11 16:40:35 -070012997 @brief deserialize from stream
12998 @deprecated This stream operator is deprecated and will be removed in a
12999 future version of the library. Please use
13000 @ref operator>>(std::istream&, basic_json&)
13001 instead; that is, replace calls like `j << i;` with `i >> j;`.
13002 @since version 1.0.0; deprecated since version 3.0.0
Ed Tanous3dac7492017-08-02 13:46:20 -070013003 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070013004 JSON_DEPRECATED
13005 friend std::istream& operator<<(basic_json& j, std::istream& i)
Ed Tanous3dac7492017-08-02 13:46:20 -070013006 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070013007 return operator>>(i, j);
Ed Tanous3dac7492017-08-02 13:46:20 -070013008 }
13009
13010 /*!
13011 @brief deserialize from stream
13012
13013 Deserializes an input stream to a JSON value.
13014
13015 @param[in,out] i input stream to read a serialized JSON value from
13016 @param[in,out] j JSON value to write the deserialized input to
13017
Ed Tanousba9f9a62017-10-11 16:40:35 -070013018 @throw parse_error.101 in case of an unexpected token
13019 @throw parse_error.102 if to_unicode fails or surrogate error
13020 @throw parse_error.103 if to_unicode fails
Ed Tanous3dac7492017-08-02 13:46:20 -070013021
13022 @complexity Linear in the length of the input. The parser is a predictive
13023 LL(1) parser.
13024
13025 @note A UTF-8 byte order mark is silently ignored.
13026
13027 @liveexample{The example below shows how a JSON value is constructed by
13028 reading a serialization from a stream.,operator_deserialize}
13029
13030 @sa parse(std::istream&, const parser_callback_t) for a variant with a
13031 parser callback function to filter values while parsing
13032
13033 @since version 1.0.0
13034 */
Ed Tanous3dac7492017-08-02 13:46:20 -070013035 friend std::istream& operator>>(std::istream& i, basic_json& j)
13036 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070013037 parser(detail::input_adapter(i)).parse(false, j);
Ed Tanous3dac7492017-08-02 13:46:20 -070013038 return i;
13039 }
13040
13041 /// @}
13042
Ed Tanous3dac7492017-08-02 13:46:20 -070013043 ///////////////////////////
13044 // convenience functions //
13045 ///////////////////////////
13046
13047 /*!
13048 @brief return the type as string
13049
13050 Returns the type name as string to be used in error messages - usually to
13051 indicate that a function was called on a wrong JSON type.
13052
Ed Tanousba9f9a62017-10-11 16:40:35 -070013053 @return a string representation of a the @a m_type member:
13054 Value type | return value
13055 ----------- | -------------
13056 null | `"null"`
13057 boolean | `"boolean"`
13058 string | `"string"`
13059 number | `"number"` (for all number types)
13060 object | `"object"`
13061 array | `"array"`
13062 discarded | `"discarded"`
13063
13064 @exceptionsafety No-throw guarantee: this function never throws exceptions.
Ed Tanous3dac7492017-08-02 13:46:20 -070013065
13066 @complexity Constant.
13067
13068 @liveexample{The following code exemplifies `type_name()` for all JSON
13069 types.,type_name}
13070
Ed Tanousba9f9a62017-10-11 16:40:35 -070013071 @sa @ref type() -- return the type of the JSON value
13072 @sa @ref operator value_t() -- return the type of the JSON value (implicit)
13073
13074 @since version 1.0.0, public since 2.1.0, `const char*` and `noexcept`
13075 since 3.0.0
Ed Tanous3dac7492017-08-02 13:46:20 -070013076 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070013077 const char* type_name() const noexcept
Ed Tanous3dac7492017-08-02 13:46:20 -070013078 {
13079 {
13080 switch (m_type)
13081 {
13082 case value_t::null:
13083 return "null";
13084 case value_t::object:
13085 return "object";
13086 case value_t::array:
13087 return "array";
13088 case value_t::string:
13089 return "string";
13090 case value_t::boolean:
13091 return "boolean";
13092 case value_t::discarded:
13093 return "discarded";
13094 default:
13095 return "number";
13096 }
13097 }
13098 }
13099
Ed Tanous3dac7492017-08-02 13:46:20 -070013100
13101 private:
13102 //////////////////////
13103 // member variables //
13104 //////////////////////
13105
13106 /// the type of the current element
13107 value_t m_type = value_t::null;
13108
13109 /// the value of the current element
13110 json_value m_value = {};
13111
Ed Tanousba9f9a62017-10-11 16:40:35 -070013112 //////////////////////////////////////////
13113 // binary serialization/deserialization //
13114 //////////////////////////////////////////
Ed Tanous3dac7492017-08-02 13:46:20 -070013115
Ed Tanousba9f9a62017-10-11 16:40:35 -070013116 /// @name binary serialization/deserialization support
13117 /// @{
Ed Tanous3dac7492017-08-02 13:46:20 -070013118
13119 public:
13120 /*!
Ed Tanousba9f9a62017-10-11 16:40:35 -070013121 @brief create a CBOR serialization of a given JSON value
Ed Tanous3dac7492017-08-02 13:46:20 -070013122
Ed Tanousba9f9a62017-10-11 16:40:35 -070013123 Serializes a given JSON value @a j to a byte vector using the CBOR (Concise
13124 Binary Object Representation) serialization format. CBOR is a binary
13125 serialization format which aims to be more compact than JSON itself, yet
13126 more efficient to parse.
Ed Tanous3dac7492017-08-02 13:46:20 -070013127
Ed Tanousba9f9a62017-10-11 16:40:35 -070013128 The library uses the following mapping from JSON values types to
13129 CBOR types according to the CBOR specification (RFC 7049):
Ed Tanous3dac7492017-08-02 13:46:20 -070013130
Ed Tanousba9f9a62017-10-11 16:40:35 -070013131 JSON value type | value/range | CBOR type | first byte
13132 --------------- | ------------------------------------------ | ---------------------------------- | ---------------
13133 null | `null` | Null | 0xf6
13134 boolean | `true` | True | 0xf5
13135 boolean | `false` | False | 0xf4
13136 number_integer | -9223372036854775808..-2147483649 | Negative integer (8 bytes follow) | 0x3b
13137 number_integer | -2147483648..-32769 | Negative integer (4 bytes follow) | 0x3a
13138 number_integer | -32768..-129 | Negative integer (2 bytes follow) | 0x39
13139 number_integer | -128..-25 | Negative integer (1 byte follow) | 0x38
13140 number_integer | -24..-1 | Negative integer | 0x20..0x37
13141 number_integer | 0..23 | Integer | 0x00..0x17
13142 number_integer | 24..255 | Unsigned integer (1 byte follow) | 0x18
13143 number_integer | 256..65535 | Unsigned integer (2 bytes follow) | 0x19
13144 number_integer | 65536..4294967295 | Unsigned integer (4 bytes follow) | 0x1a
13145 number_integer | 4294967296..18446744073709551615 | Unsigned integer (8 bytes follow) | 0x1b
13146 number_unsigned | 0..23 | Integer | 0x00..0x17
13147 number_unsigned | 24..255 | Unsigned integer (1 byte follow) | 0x18
13148 number_unsigned | 256..65535 | Unsigned integer (2 bytes follow) | 0x19
13149 number_unsigned | 65536..4294967295 | Unsigned integer (4 bytes follow) | 0x1a
13150 number_unsigned | 4294967296..18446744073709551615 | Unsigned integer (8 bytes follow) | 0x1b
13151 number_float | *any value* | Double-Precision Float | 0xfb
13152 string | *length*: 0..23 | UTF-8 string | 0x60..0x77
13153 string | *length*: 23..255 | UTF-8 string (1 byte follow) | 0x78
13154 string | *length*: 256..65535 | UTF-8 string (2 bytes follow) | 0x79
13155 string | *length*: 65536..4294967295 | UTF-8 string (4 bytes follow) | 0x7a
13156 string | *length*: 4294967296..18446744073709551615 | UTF-8 string (8 bytes follow) | 0x7b
13157 array | *size*: 0..23 | array | 0x80..0x97
13158 array | *size*: 23..255 | array (1 byte follow) | 0x98
13159 array | *size*: 256..65535 | array (2 bytes follow) | 0x99
13160 array | *size*: 65536..4294967295 | array (4 bytes follow) | 0x9a
13161 array | *size*: 4294967296..18446744073709551615 | array (8 bytes follow) | 0x9b
13162 object | *size*: 0..23 | map | 0xa0..0xb7
13163 object | *size*: 23..255 | map (1 byte follow) | 0xb8
13164 object | *size*: 256..65535 | map (2 bytes follow) | 0xb9
13165 object | *size*: 65536..4294967295 | map (4 bytes follow) | 0xba
13166 object | *size*: 4294967296..18446744073709551615 | map (8 bytes follow) | 0xbb
Ed Tanous3dac7492017-08-02 13:46:20 -070013167
Ed Tanousba9f9a62017-10-11 16:40:35 -070013168 @note The mapping is **complete** in the sense that any JSON value type
13169 can be converted to a CBOR value.
13170
13171 @note If NaN or Infinity are stored inside a JSON number, they are
13172 serialized properly. This behavior differs from the @ref dump()
13173 function which serializes NaN or Infinity to `null`.
13174
13175 @note The following CBOR types are not used in the conversion:
13176 - byte strings (0x40..0x5f)
13177 - UTF-8 strings terminated by "break" (0x7f)
13178 - arrays terminated by "break" (0x9f)
13179 - maps terminated by "break" (0xbf)
13180 - date/time (0xc0..0xc1)
13181 - bignum (0xc2..0xc3)
13182 - decimal fraction (0xc4)
13183 - bigfloat (0xc5)
13184 - tagged items (0xc6..0xd4, 0xd8..0xdb)
13185 - expected conversions (0xd5..0xd7)
13186 - simple values (0xe0..0xf3, 0xf8)
13187 - undefined (0xf7)
13188 - half and single-precision floats (0xf9-0xfa)
13189 - break (0xff)
13190
13191 @param[in] j JSON value to serialize
13192 @return MessagePack serialization as byte vector
13193
13194 @complexity Linear in the size of the JSON value @a j.
13195
13196 @liveexample{The example shows the serialization of a JSON value to a byte
13197 vector in CBOR format.,to_cbor}
13198
13199 @sa http://cbor.io
13200 @sa @ref from_cbor(const std::vector<uint8_t>&, const size_t) for the
13201 analogous deserialization
13202 @sa @ref to_msgpack(const basic_json&) for the related MessagePack format
13203
13204 @since version 2.0.9
Ed Tanous3dac7492017-08-02 13:46:20 -070013205 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070013206 static std::vector<uint8_t> to_cbor(const basic_json& j)
Ed Tanous3dac7492017-08-02 13:46:20 -070013207 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070013208 std::vector<uint8_t> result;
13209 to_cbor(j, result);
13210 return result;
13211 }
Ed Tanous3dac7492017-08-02 13:46:20 -070013212
Ed Tanousba9f9a62017-10-11 16:40:35 -070013213 static void to_cbor(const basic_json& j, detail::output_adapter<uint8_t> o)
13214 {
13215 binary_writer<uint8_t>(o).write_cbor(j);
13216 }
Ed Tanous3dac7492017-08-02 13:46:20 -070013217
Ed Tanousba9f9a62017-10-11 16:40:35 -070013218 static void to_cbor(const basic_json& j, detail::output_adapter<char> o)
13219 {
13220 binary_writer<char>(o).write_cbor(j);
13221 }
Ed Tanous3dac7492017-08-02 13:46:20 -070013222
13223 /*!
Ed Tanousba9f9a62017-10-11 16:40:35 -070013224 @brief create a MessagePack serialization of a given JSON value
Ed Tanous3dac7492017-08-02 13:46:20 -070013225
Ed Tanousba9f9a62017-10-11 16:40:35 -070013226 Serializes a given JSON value @a j to a byte vector using the MessagePack
13227 serialization format. MessagePack is a binary serialization format which
13228 aims to be more compact than JSON itself, yet more efficient to parse.
Ed Tanous3dac7492017-08-02 13:46:20 -070013229
Ed Tanousba9f9a62017-10-11 16:40:35 -070013230 The library uses the following mapping from JSON values types to
13231 MessagePack types according to the MessagePack specification:
Ed Tanous3dac7492017-08-02 13:46:20 -070013232
Ed Tanousba9f9a62017-10-11 16:40:35 -070013233 JSON value type | value/range | MessagePack type | first byte
13234 --------------- | --------------------------------- | ---------------- | ----------
13235 null | `null` | nil | 0xc0
13236 boolean | `true` | true | 0xc3
13237 boolean | `false` | false | 0xc2
13238 number_integer | -9223372036854775808..-2147483649 | int64 | 0xd3
13239 number_integer | -2147483648..-32769 | int32 | 0xd2
13240 number_integer | -32768..-129 | int16 | 0xd1
13241 number_integer | -128..-33 | int8 | 0xd0
13242 number_integer | -32..-1 | negative fixint | 0xe0..0xff
13243 number_integer | 0..127 | positive fixint | 0x00..0x7f
13244 number_integer | 128..255 | uint 8 | 0xcc
13245 number_integer | 256..65535 | uint 16 | 0xcd
13246 number_integer | 65536..4294967295 | uint 32 | 0xce
13247 number_integer | 4294967296..18446744073709551615 | uint 64 | 0xcf
13248 number_unsigned | 0..127 | positive fixint | 0x00..0x7f
13249 number_unsigned | 128..255 | uint 8 | 0xcc
13250 number_unsigned | 256..65535 | uint 16 | 0xcd
13251 number_unsigned | 65536..4294967295 | uint 32 | 0xce
13252 number_unsigned | 4294967296..18446744073709551615 | uint 64 | 0xcf
13253 number_float | *any value* | float 64 | 0xcb
13254 string | *length*: 0..31 | fixstr | 0xa0..0xbf
13255 string | *length*: 32..255 | str 8 | 0xd9
13256 string | *length*: 256..65535 | str 16 | 0xda
13257 string | *length*: 65536..4294967295 | str 32 | 0xdb
13258 array | *size*: 0..15 | fixarray | 0x90..0x9f
13259 array | *size*: 16..65535 | array 16 | 0xdc
13260 array | *size*: 65536..4294967295 | array 32 | 0xdd
13261 object | *size*: 0..15 | fix map | 0x80..0x8f
13262 object | *size*: 16..65535 | map 16 | 0xde
13263 object | *size*: 65536..4294967295 | map 32 | 0xdf
13264
13265 @note The mapping is **complete** in the sense that any JSON value type
13266 can be converted to a MessagePack value.
13267
13268 @note The following values can **not** be converted to a MessagePack value:
13269 - strings with more than 4294967295 bytes
13270 - arrays with more than 4294967295 elements
13271 - objects with more than 4294967295 elements
13272
13273 @note The following MessagePack types are not used in the conversion:
13274 - bin 8 - bin 32 (0xc4..0xc6)
13275 - ext 8 - ext 32 (0xc7..0xc9)
13276 - float 32 (0xca)
13277 - fixext 1 - fixext 16 (0xd4..0xd8)
13278
13279 @note Any MessagePack output created @ref to_msgpack can be successfully
13280 parsed by @ref from_msgpack.
13281
13282 @note If NaN or Infinity are stored inside a JSON number, they are
13283 serialized properly. This behavior differs from the @ref dump()
13284 function which serializes NaN or Infinity to `null`.
13285
13286 @param[in] j JSON value to serialize
13287 @return MessagePack serialization as byte vector
13288
13289 @complexity Linear in the size of the JSON value @a j.
13290
13291 @liveexample{The example shows the serialization of a JSON value to a byte
13292 vector in MessagePack format.,to_msgpack}
13293
13294 @sa http://msgpack.org
13295 @sa @ref from_msgpack(const std::vector<uint8_t>&, const size_t) for the
13296 analogous deserialization
13297 @sa @ref to_cbor(const basic_json& for the related CBOR format
13298
13299 @since version 2.0.9
Ed Tanous3dac7492017-08-02 13:46:20 -070013300 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070013301 static std::vector<uint8_t> to_msgpack(const basic_json& j)
Ed Tanous3dac7492017-08-02 13:46:20 -070013302 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070013303 std::vector<uint8_t> result;
13304 to_msgpack(j, result);
13305 return result;
13306 }
Ed Tanous3dac7492017-08-02 13:46:20 -070013307
Ed Tanousba9f9a62017-10-11 16:40:35 -070013308 static void to_msgpack(const basic_json& j, detail::output_adapter<uint8_t> o)
13309 {
13310 binary_writer<uint8_t>(o).write_msgpack(j);
13311 }
Ed Tanous3dac7492017-08-02 13:46:20 -070013312
Ed Tanousba9f9a62017-10-11 16:40:35 -070013313 static void to_msgpack(const basic_json& j, detail::output_adapter<char> o)
13314 {
13315 binary_writer<char>(o).write_msgpack(j);
13316 }
Ed Tanous3dac7492017-08-02 13:46:20 -070013317
13318 /*!
Ed Tanousba9f9a62017-10-11 16:40:35 -070013319 @brief create a JSON value from an input in CBOR format
Ed Tanous3dac7492017-08-02 13:46:20 -070013320
Ed Tanousba9f9a62017-10-11 16:40:35 -070013321 Deserializes a given input @a i to a JSON value using the CBOR (Concise
13322 Binary Object Representation) serialization format.
13323
13324 The library maps CBOR types to JSON value types as follows:
13325
13326 CBOR type | JSON value type | first byte
13327 ---------------------- | --------------- | ----------
13328 Integer | number_unsigned | 0x00..0x17
13329 Unsigned integer | number_unsigned | 0x18
13330 Unsigned integer | number_unsigned | 0x19
13331 Unsigned integer | number_unsigned | 0x1a
13332 Unsigned integer | number_unsigned | 0x1b
13333 Negative integer | number_integer | 0x20..0x37
13334 Negative integer | number_integer | 0x38
13335 Negative integer | number_integer | 0x39
13336 Negative integer | number_integer | 0x3a
13337 Negative integer | number_integer | 0x3b
13338 Negative integer | number_integer | 0x40..0x57
13339 UTF-8 string | string | 0x60..0x77
13340 UTF-8 string | string | 0x78
13341 UTF-8 string | string | 0x79
13342 UTF-8 string | string | 0x7a
13343 UTF-8 string | string | 0x7b
13344 UTF-8 string | string | 0x7f
13345 array | array | 0x80..0x97
13346 array | array | 0x98
13347 array | array | 0x99
13348 array | array | 0x9a
13349 array | array | 0x9b
13350 array | array | 0x9f
13351 map | object | 0xa0..0xb7
13352 map | object | 0xb8
13353 map | object | 0xb9
13354 map | object | 0xba
13355 map | object | 0xbb
13356 map | object | 0xbf
13357 False | `false` | 0xf4
13358 True | `true` | 0xf5
13359 Nill | `null` | 0xf6
13360 Half-Precision Float | number_float | 0xf9
13361 Single-Precision Float | number_float | 0xfa
13362 Double-Precision Float | number_float | 0xfb
13363
13364 @warning The mapping is **incomplete** in the sense that not all CBOR
13365 types can be converted to a JSON value. The following CBOR types
13366 are not supported and will yield parse errors (parse_error.112):
13367 - byte strings (0x40..0x5f)
13368 - date/time (0xc0..0xc1)
13369 - bignum (0xc2..0xc3)
13370 - decimal fraction (0xc4)
13371 - bigfloat (0xc5)
13372 - tagged items (0xc6..0xd4, 0xd8..0xdb)
13373 - expected conversions (0xd5..0xd7)
13374 - simple values (0xe0..0xf3, 0xf8)
13375 - undefined (0xf7)
13376
13377 @warning CBOR allows map keys of any type, whereas JSON only allows
13378 strings as keys in object values. Therefore, CBOR maps with keys
13379 other than UTF-8 strings are rejected (parse_error.113).
13380
13381 @note Any CBOR output created @ref to_cbor can be successfully parsed by
13382 @ref from_cbor.
13383
13384 @param[in] i an input in CBOR format convertible to an input adapter
13385 @param[in] strict whether to expect the input to be consumed until EOF
13386 (true by default)
13387 @return deserialized JSON value
13388
13389 @throw parse_error.110 if the given input ends prematurely or the end of
13390 file was not reached when @a strict was set to true
13391 @throw parse_error.112 if unsupported features from CBOR were
13392 used in the given input @a v or if the input is not valid CBOR
13393 @throw parse_error.113 if a string was expected as map key, but not found
13394
13395 @complexity Linear in the size of the input @a i.
13396
13397 @liveexample{The example shows the deserialization of a byte vector in CBOR
13398 format to a JSON value.,from_cbor}
13399
13400 @sa http://cbor.io
13401 @sa @ref to_cbor(const basic_json&) for the analogous serialization
13402 @sa @ref from_msgpack(detail::input_adapter, const bool) for the
13403 related MessagePack format
13404
13405 @since version 2.0.9; parameter @a start_index since 2.1.1; changed to
13406 consume input adapters, removed start_index parameter, and added
13407 @a strict parameter since 3.0.0
Ed Tanous3dac7492017-08-02 13:46:20 -070013408 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070013409 static basic_json from_cbor(detail::input_adapter i,
13410 const bool strict = true)
Ed Tanous3dac7492017-08-02 13:46:20 -070013411 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070013412 return binary_reader(i).parse_cbor(strict);
13413 }
Ed Tanous3dac7492017-08-02 13:46:20 -070013414
13415 /*!
Ed Tanousba9f9a62017-10-11 16:40:35 -070013416 @copydoc from_cbor(detail::input_adapter, const bool)
Ed Tanous3dac7492017-08-02 13:46:20 -070013417 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070013418 template<typename A1, typename A2,
13419 detail::enable_if_t<std::is_constructible<detail::input_adapter, A1, A2>::value, int> = 0>
13420 static basic_json from_cbor(A1 && a1, A2 && a2, const bool strict = true)
Ed Tanous3dac7492017-08-02 13:46:20 -070013421 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070013422 return binary_reader(detail::input_adapter(std::forward<A1>(a1), std::forward<A2>(a2))).parse_cbor(strict);
13423 }
Ed Tanous3dac7492017-08-02 13:46:20 -070013424
Ed Tanous3dac7492017-08-02 13:46:20 -070013425 /*!
Ed Tanousba9f9a62017-10-11 16:40:35 -070013426 @brief create a JSON value from an input in MessagePack format
Ed Tanous3dac7492017-08-02 13:46:20 -070013427
Ed Tanousba9f9a62017-10-11 16:40:35 -070013428 Deserializes a given input @a i to a JSON value using the MessagePack
13429 serialization format.
Ed Tanous3dac7492017-08-02 13:46:20 -070013430
Ed Tanousba9f9a62017-10-11 16:40:35 -070013431 The library maps MessagePack types to JSON value types as follows:
Ed Tanous3dac7492017-08-02 13:46:20 -070013432
Ed Tanousba9f9a62017-10-11 16:40:35 -070013433 MessagePack type | JSON value type | first byte
13434 ---------------- | --------------- | ----------
13435 positive fixint | number_unsigned | 0x00..0x7f
13436 fixmap | object | 0x80..0x8f
13437 fixarray | array | 0x90..0x9f
13438 fixstr | string | 0xa0..0xbf
13439 nil | `null` | 0xc0
13440 false | `false` | 0xc2
13441 true | `true` | 0xc3
13442 float 32 | number_float | 0xca
13443 float 64 | number_float | 0xcb
13444 uint 8 | number_unsigned | 0xcc
13445 uint 16 | number_unsigned | 0xcd
13446 uint 32 | number_unsigned | 0xce
13447 uint 64 | number_unsigned | 0xcf
13448 int 8 | number_integer | 0xd0
13449 int 16 | number_integer | 0xd1
13450 int 32 | number_integer | 0xd2
13451 int 64 | number_integer | 0xd3
13452 str 8 | string | 0xd9
13453 str 16 | string | 0xda
13454 str 32 | string | 0xdb
13455 array 16 | array | 0xdc
13456 array 32 | array | 0xdd
13457 map 16 | object | 0xde
13458 map 32 | object | 0xdf
13459 negative fixint | number_integer | 0xe0-0xff
13460
13461 @warning The mapping is **incomplete** in the sense that not all
13462 MessagePack types can be converted to a JSON value. The following
13463 MessagePack types are not supported and will yield parse errors:
13464 - bin 8 - bin 32 (0xc4..0xc6)
13465 - ext 8 - ext 32 (0xc7..0xc9)
13466 - fixext 1 - fixext 16 (0xd4..0xd8)
13467
13468 @note Any MessagePack output created @ref to_msgpack can be successfully
13469 parsed by @ref from_msgpack.
13470
13471 @param[in] i an input in MessagePack format convertible to an input
13472 adapter
13473 @param[in] strict whether to expect the input to be consumed until EOF
13474 (true by default)
13475
13476 @throw parse_error.110 if the given input ends prematurely or the end of
13477 file was not reached when @a strict was set to true
13478 @throw parse_error.112 if unsupported features from MessagePack were
13479 used in the given input @a i or if the input is not valid MessagePack
13480 @throw parse_error.113 if a string was expected as map key, but not found
13481
13482 @complexity Linear in the size of the input @a i.
13483
13484 @liveexample{The example shows the deserialization of a byte vector in
13485 MessagePack format to a JSON value.,from_msgpack}
13486
13487 @sa http://msgpack.org
13488 @sa @ref to_msgpack(const basic_json&) for the analogous serialization
13489 @sa @ref from_cbor(detail::input_adapter, const bool) for the related CBOR
13490 format
13491
13492 @since version 2.0.9; parameter @a start_index since 2.1.1; changed to
13493 consume input adapters, removed start_index parameter, and added
13494 @a strict parameter since 3.0.0
Ed Tanous3dac7492017-08-02 13:46:20 -070013495 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070013496 static basic_json from_msgpack(detail::input_adapter i,
13497 const bool strict = true)
Ed Tanous3dac7492017-08-02 13:46:20 -070013498 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070013499 return binary_reader(i).parse_msgpack(strict);
13500 }
Ed Tanous3dac7492017-08-02 13:46:20 -070013501
Ed Tanousba9f9a62017-10-11 16:40:35 -070013502 /*!
13503 @copydoc from_msgpack(detail::input_adapter, const bool)
13504 */
13505 template<typename A1, typename A2,
13506 detail::enable_if_t<std::is_constructible<detail::input_adapter, A1, A2>::value, int> = 0>
13507 static basic_json from_msgpack(A1 && a1, A2 && a2, const bool strict = true)
13508 {
13509 return binary_reader(detail::input_adapter(std::forward<A1>(a1), std::forward<A2>(a2))).parse_msgpack(strict);
13510 }
Ed Tanous3dac7492017-08-02 13:46:20 -070013511
Ed Tanousba9f9a62017-10-11 16:40:35 -070013512 /// @}
Ed Tanous3dac7492017-08-02 13:46:20 -070013513
13514 //////////////////////////
13515 // JSON Pointer support //
13516 //////////////////////////
13517
13518 /// @name JSON Pointer functions
13519 /// @{
13520
13521 /*!
13522 @brief access specified element via JSON Pointer
13523
13524 Uses a JSON pointer to retrieve a reference to the respective JSON value.
13525 No bound checking is performed. Similar to @ref operator[](const typename
13526 object_t::key_type&), `null` values are created in arrays and objects if
13527 necessary.
13528
13529 In particular:
13530 - If the JSON pointer points to an object key that does not exist, it
13531 is created an filled with a `null` value before a reference to it
13532 is returned.
13533 - If the JSON pointer points to an array index that does not exist, it
13534 is created an filled with a `null` value before a reference to it
13535 is returned. All indices between the current maximum and the given
13536 index are also filled with `null`.
13537 - The special value `-` is treated as a synonym for the index past the
13538 end.
13539
13540 @param[in] ptr a JSON pointer
13541
13542 @return reference to the element pointed to by @a ptr
13543
13544 @complexity Constant.
13545
Ed Tanousba9f9a62017-10-11 16:40:35 -070013546 @throw parse_error.106 if an array index begins with '0'
13547 @throw parse_error.109 if an array index was not a number
13548 @throw out_of_range.404 if the JSON pointer can not be resolved
Ed Tanous3dac7492017-08-02 13:46:20 -070013549
13550 @liveexample{The behavior is shown in the example.,operatorjson_pointer}
13551
13552 @since version 2.0.0
13553 */
13554 reference operator[](const json_pointer& ptr)
13555 {
13556 return ptr.get_unchecked(this);
13557 }
13558
13559 /*!
13560 @brief access specified element via JSON Pointer
13561
13562 Uses a JSON pointer to retrieve a reference to the respective JSON value.
13563 No bound checking is performed. The function does not change the JSON
13564 value; no `null` values are created. In particular, the the special value
13565 `-` yields an exception.
13566
13567 @param[in] ptr JSON pointer to the desired element
13568
13569 @return const reference to the element pointed to by @a ptr
13570
13571 @complexity Constant.
13572
Ed Tanousba9f9a62017-10-11 16:40:35 -070013573 @throw parse_error.106 if an array index begins with '0'
13574 @throw parse_error.109 if an array index was not a number
13575 @throw out_of_range.402 if the array index '-' is used
13576 @throw out_of_range.404 if the JSON pointer can not be resolved
Ed Tanous3dac7492017-08-02 13:46:20 -070013577
13578 @liveexample{The behavior is shown in the example.,operatorjson_pointer_const}
13579
13580 @since version 2.0.0
13581 */
13582 const_reference operator[](const json_pointer& ptr) const
13583 {
13584 return ptr.get_unchecked(this);
13585 }
13586
13587 /*!
13588 @brief access specified element via JSON Pointer
13589
13590 Returns a reference to the element at with specified JSON pointer @a ptr,
13591 with bounds checking.
13592
13593 @param[in] ptr JSON pointer to the desired element
13594
13595 @return reference to the element pointed to by @a ptr
13596
Ed Tanousba9f9a62017-10-11 16:40:35 -070013597 @throw parse_error.106 if an array index in the passed JSON pointer @a ptr
13598 begins with '0'. See example below.
13599
13600 @throw parse_error.109 if an array index in the passed JSON pointer @a ptr
13601 is not a number. See example below.
13602
13603 @throw out_of_range.401 if an array index in the passed JSON pointer @a ptr
13604 is out of range. See example below.
13605
13606 @throw out_of_range.402 if the array index '-' is used in the passed JSON
13607 pointer @a ptr. As `at` provides checked access (and no elements are
13608 implicitly inserted), the index '-' is always invalid. See example below.
13609
13610 @throw out_of_range.404 if the JSON pointer @a ptr can not be resolved.
13611 See example below.
13612
13613 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
13614 changes in the JSON value.
13615
Ed Tanous3dac7492017-08-02 13:46:20 -070013616 @complexity Constant.
13617
Ed Tanousba9f9a62017-10-11 16:40:35 -070013618 @since version 2.0.0
Ed Tanous3dac7492017-08-02 13:46:20 -070013619
13620 @liveexample{The behavior is shown in the example.,at_json_pointer}
Ed Tanous3dac7492017-08-02 13:46:20 -070013621 */
13622 reference at(const json_pointer& ptr)
13623 {
13624 return ptr.get_checked(this);
13625 }
13626
13627 /*!
13628 @brief access specified element via JSON Pointer
13629
13630 Returns a const reference to the element at with specified JSON pointer @a
13631 ptr, with bounds checking.
13632
13633 @param[in] ptr JSON pointer to the desired element
13634
13635 @return reference to the element pointed to by @a ptr
13636
Ed Tanousba9f9a62017-10-11 16:40:35 -070013637 @throw parse_error.106 if an array index in the passed JSON pointer @a ptr
13638 begins with '0'. See example below.
13639
13640 @throw parse_error.109 if an array index in the passed JSON pointer @a ptr
13641 is not a number. See example below.
13642
13643 @throw out_of_range.401 if an array index in the passed JSON pointer @a ptr
13644 is out of range. See example below.
13645
13646 @throw out_of_range.402 if the array index '-' is used in the passed JSON
13647 pointer @a ptr. As `at` provides checked access (and no elements are
13648 implicitly inserted), the index '-' is always invalid. See example below.
13649
13650 @throw out_of_range.404 if the JSON pointer @a ptr can not be resolved.
13651 See example below.
13652
13653 @exceptionsafety Strong guarantee: if an exception is thrown, there are no
13654 changes in the JSON value.
13655
Ed Tanous3dac7492017-08-02 13:46:20 -070013656 @complexity Constant.
13657
Ed Tanousba9f9a62017-10-11 16:40:35 -070013658 @since version 2.0.0
Ed Tanous3dac7492017-08-02 13:46:20 -070013659
13660 @liveexample{The behavior is shown in the example.,at_json_pointer_const}
Ed Tanous3dac7492017-08-02 13:46:20 -070013661 */
13662 const_reference at(const json_pointer& ptr) const
13663 {
13664 return ptr.get_checked(this);
13665 }
13666
13667 /*!
13668 @brief return flattened JSON value
13669
13670 The function creates a JSON object whose keys are JSON pointers (see [RFC
13671 6901](https://tools.ietf.org/html/rfc6901)) and whose values are all
13672 primitive. The original JSON value can be restored using the @ref
13673 unflatten() function.
13674
13675 @return an object that maps JSON pointers to primitive values
13676
13677 @note Empty objects and arrays are flattened to `null` and will not be
13678 reconstructed correctly by the @ref unflatten() function.
13679
13680 @complexity Linear in the size the JSON value.
13681
13682 @liveexample{The following code shows how a JSON object is flattened to an
13683 object whose keys consist of JSON pointers.,flatten}
13684
13685 @sa @ref unflatten() for the reverse function
13686
13687 @since version 2.0.0
13688 */
13689 basic_json flatten() const
13690 {
13691 basic_json result(value_t::object);
13692 json_pointer::flatten("", *this, result);
13693 return result;
13694 }
13695
13696 /*!
13697 @brief unflatten a previously flattened JSON value
13698
13699 The function restores the arbitrary nesting of a JSON value that has been
13700 flattened before using the @ref flatten() function. The JSON value must
13701 meet certain constraints:
13702 1. The value must be an object.
13703 2. The keys must be JSON pointers (see
13704 [RFC 6901](https://tools.ietf.org/html/rfc6901))
13705 3. The mapped values must be primitive JSON types.
13706
13707 @return the original JSON from a flattened version
13708
13709 @note Empty objects and arrays are flattened by @ref flatten() to `null`
13710 values and can not unflattened to their original type. Apart from
13711 this example, for a JSON value `j`, the following is always true:
13712 `j == j.flatten().unflatten()`.
13713
13714 @complexity Linear in the size the JSON value.
13715
Ed Tanousba9f9a62017-10-11 16:40:35 -070013716 @throw type_error.314 if value is not an object
13717 @throw type_error.315 if object values are not primitive
13718
Ed Tanous3dac7492017-08-02 13:46:20 -070013719 @liveexample{The following code shows how a flattened JSON object is
13720 unflattened into the original nested JSON object.,unflatten}
13721
13722 @sa @ref flatten() for the reverse function
13723
13724 @since version 2.0.0
13725 */
13726 basic_json unflatten() const
13727 {
13728 return json_pointer::unflatten(*this);
13729 }
13730
13731 /// @}
13732
13733 //////////////////////////
13734 // JSON Patch functions //
13735 //////////////////////////
13736
13737 /// @name JSON Patch functions
13738 /// @{
13739
13740 /*!
13741 @brief applies a JSON patch
13742
13743 [JSON Patch](http://jsonpatch.com) defines a JSON document structure for
13744 expressing a sequence of operations to apply to a JSON) document. With
13745 this function, a JSON Patch is applied to the current JSON value by
13746 executing all operations from the patch.
13747
13748 @param[in] json_patch JSON patch document
13749 @return patched document
13750
13751 @note The application of a patch is atomic: Either all operations succeed
13752 and the patched document is returned or an exception is thrown. In
13753 any case, the original value is not changed: the patch is applied
13754 to a copy of the value.
13755
Ed Tanousba9f9a62017-10-11 16:40:35 -070013756 @throw parse_error.104 if the JSON patch does not consist of an array of
13757 objects
13758
13759 @throw parse_error.105 if the JSON patch is malformed (e.g., mandatory
Ed Tanous3dac7492017-08-02 13:46:20 -070013760 attributes are missing); example: `"operation add must have member path"`
13761
Ed Tanousba9f9a62017-10-11 16:40:35 -070013762 @throw out_of_range.401 if an array index is out of range.
13763
13764 @throw out_of_range.403 if a JSON pointer inside the patch could not be
13765 resolved successfully in the current JSON value; example: `"key baz not
13766 found"`
13767
13768 @throw out_of_range.405 if JSON pointer has no parent ("add", "remove",
13769 "move")
13770
13771 @throw other_error.501 if "test" operation was unsuccessful
13772
Ed Tanous3dac7492017-08-02 13:46:20 -070013773 @complexity Linear in the size of the JSON value and the length of the
13774 JSON patch. As usually only a fraction of the JSON value is affected by
13775 the patch, the complexity can usually be neglected.
13776
13777 @liveexample{The following code shows how a JSON patch is applied to a
13778 value.,patch}
13779
13780 @sa @ref diff -- create a JSON patch by comparing two JSON values
13781
13782 @sa [RFC 6902 (JSON Patch)](https://tools.ietf.org/html/rfc6902)
13783 @sa [RFC 6901 (JSON Pointer)](https://tools.ietf.org/html/rfc6901)
13784
13785 @since version 2.0.0
13786 */
13787 basic_json patch(const basic_json& json_patch) const
13788 {
13789 // make a working copy to apply the patch to
13790 basic_json result = *this;
13791
13792 // the valid JSON Patch operations
13793 enum class patch_operations {add, remove, replace, move, copy, test, invalid};
13794
Ed Tanousba9f9a62017-10-11 16:40:35 -070013795 const auto get_op = [](const std::string & op)
Ed Tanous3dac7492017-08-02 13:46:20 -070013796 {
13797 if (op == "add")
13798 {
13799 return patch_operations::add;
13800 }
13801 if (op == "remove")
13802 {
13803 return patch_operations::remove;
13804 }
13805 if (op == "replace")
13806 {
13807 return patch_operations::replace;
13808 }
13809 if (op == "move")
13810 {
13811 return patch_operations::move;
13812 }
13813 if (op == "copy")
13814 {
13815 return patch_operations::copy;
13816 }
13817 if (op == "test")
13818 {
13819 return patch_operations::test;
13820 }
13821
13822 return patch_operations::invalid;
13823 };
13824
13825 // wrapper for "add" operation; add value at ptr
13826 const auto operation_add = [&result](json_pointer & ptr, basic_json val)
13827 {
13828 // adding to the root of the target document means replacing it
13829 if (ptr.is_root())
13830 {
13831 result = val;
13832 }
13833 else
13834 {
13835 // make sure the top element of the pointer exists
13836 json_pointer top_pointer = ptr.top();
13837 if (top_pointer != ptr)
13838 {
13839 result.at(top_pointer);
13840 }
13841
13842 // get reference to parent of JSON pointer ptr
13843 const auto last_path = ptr.pop_back();
13844 basic_json& parent = result[ptr];
13845
13846 switch (parent.m_type)
13847 {
13848 case value_t::null:
13849 case value_t::object:
13850 {
13851 // use operator[] to add value
13852 parent[last_path] = val;
13853 break;
13854 }
13855
13856 case value_t::array:
13857 {
13858 if (last_path == "-")
13859 {
13860 // special case: append to back
13861 parent.push_back(val);
13862 }
13863 else
13864 {
13865 const auto idx = std::stoi(last_path);
Ed Tanousba9f9a62017-10-11 16:40:35 -070013866 if (JSON_UNLIKELY(static_cast<size_type>(idx) > parent.size()))
Ed Tanous3dac7492017-08-02 13:46:20 -070013867 {
13868 // avoid undefined behavior
Ed Tanousba9f9a62017-10-11 16:40:35 -070013869 JSON_THROW(out_of_range::create(401, "array index " + std::to_string(idx) + " is out of range"));
Ed Tanous3dac7492017-08-02 13:46:20 -070013870 }
13871 else
13872 {
13873 // default case: insert add offset
13874 parent.insert(parent.begin() + static_cast<difference_type>(idx), val);
13875 }
13876 }
13877 break;
13878 }
13879
13880 default:
13881 {
13882 // if there exists a parent it cannot be primitive
13883 assert(false); // LCOV_EXCL_LINE
13884 }
13885 }
13886 }
13887 };
13888
13889 // wrapper for "remove" operation; remove value at ptr
13890 const auto operation_remove = [&result](json_pointer & ptr)
13891 {
13892 // get reference to parent of JSON pointer ptr
13893 const auto last_path = ptr.pop_back();
13894 basic_json& parent = result.at(ptr);
13895
13896 // remove child
13897 if (parent.is_object())
13898 {
13899 // perform range check
13900 auto it = parent.find(last_path);
Ed Tanousba9f9a62017-10-11 16:40:35 -070013901 if (JSON_LIKELY(it != parent.end()))
Ed Tanous3dac7492017-08-02 13:46:20 -070013902 {
13903 parent.erase(it);
13904 }
13905 else
13906 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070013907 JSON_THROW(out_of_range::create(403, "key '" + last_path + "' not found"));
Ed Tanous3dac7492017-08-02 13:46:20 -070013908 }
13909 }
13910 else if (parent.is_array())
13911 {
13912 // note erase performs range check
13913 parent.erase(static_cast<size_type>(std::stoi(last_path)));
13914 }
13915 };
13916
Ed Tanousba9f9a62017-10-11 16:40:35 -070013917 // type check: top level value must be an array
13918 if (JSON_UNLIKELY(not json_patch.is_array()))
Ed Tanous3dac7492017-08-02 13:46:20 -070013919 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070013920 JSON_THROW(parse_error::create(104, 0, "JSON patch must be an array of objects"));
Ed Tanous3dac7492017-08-02 13:46:20 -070013921 }
13922
13923 // iterate and apply the operations
13924 for (const auto& val : json_patch)
13925 {
13926 // wrapper to get a value for an operation
13927 const auto get_value = [&val](const std::string & op,
13928 const std::string & member,
13929 bool string_type) -> basic_json&
13930 {
13931 // find value
13932 auto it = val.m_value.object->find(member);
13933
13934 // context-sensitive error message
13935 const auto error_msg = (op == "op") ? "operation" : "operation '" + op + "'";
13936
13937 // check if desired value is present
Ed Tanousba9f9a62017-10-11 16:40:35 -070013938 if (JSON_UNLIKELY(it == val.m_value.object->end()))
Ed Tanous3dac7492017-08-02 13:46:20 -070013939 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070013940 JSON_THROW(parse_error::create(105, 0, error_msg + " must have member '" + member + "'"));
Ed Tanous3dac7492017-08-02 13:46:20 -070013941 }
13942
13943 // check if result is of type string
Ed Tanousba9f9a62017-10-11 16:40:35 -070013944 if (JSON_UNLIKELY(string_type and not it->second.is_string()))
Ed Tanous3dac7492017-08-02 13:46:20 -070013945 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070013946 JSON_THROW(parse_error::create(105, 0, error_msg + " must have string member '" + member + "'"));
Ed Tanous3dac7492017-08-02 13:46:20 -070013947 }
13948
13949 // no error: return value
13950 return it->second;
13951 };
13952
Ed Tanousba9f9a62017-10-11 16:40:35 -070013953 // type check: every element of the array must be an object
13954 if (JSON_UNLIKELY(not val.is_object()))
Ed Tanous3dac7492017-08-02 13:46:20 -070013955 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070013956 JSON_THROW(parse_error::create(104, 0, "JSON patch must be an array of objects"));
Ed Tanous3dac7492017-08-02 13:46:20 -070013957 }
13958
13959 // collect mandatory members
13960 const std::string op = get_value("op", "op", true);
13961 const std::string path = get_value(op, "path", true);
13962 json_pointer ptr(path);
13963
13964 switch (get_op(op))
13965 {
13966 case patch_operations::add:
13967 {
13968 operation_add(ptr, get_value("add", "value", false));
13969 break;
13970 }
13971
13972 case patch_operations::remove:
13973 {
13974 operation_remove(ptr);
13975 break;
13976 }
13977
13978 case patch_operations::replace:
13979 {
13980 // the "path" location must exist - use at()
13981 result.at(ptr) = get_value("replace", "value", false);
13982 break;
13983 }
13984
13985 case patch_operations::move:
13986 {
13987 const std::string from_path = get_value("move", "from", true);
13988 json_pointer from_ptr(from_path);
13989
13990 // the "from" location must exist - use at()
13991 basic_json v = result.at(from_ptr);
13992
13993 // The move operation is functionally identical to a
13994 // "remove" operation on the "from" location, followed
13995 // immediately by an "add" operation at the target
13996 // location with the value that was just removed.
13997 operation_remove(from_ptr);
13998 operation_add(ptr, v);
13999 break;
14000 }
14001
14002 case patch_operations::copy:
14003 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070014004 const std::string from_path = get_value("copy", "from", true);
Ed Tanous3dac7492017-08-02 13:46:20 -070014005 const json_pointer from_ptr(from_path);
14006
14007 // the "from" location must exist - use at()
14008 result[ptr] = result.at(from_ptr);
14009 break;
14010 }
14011
14012 case patch_operations::test:
14013 {
14014 bool success = false;
14015 JSON_TRY
14016 {
14017 // check if "value" matches the one at "path"
14018 // the "path" location must exist - use at()
14019 success = (result.at(ptr) == get_value("test", "value", false));
14020 }
Ed Tanousba9f9a62017-10-11 16:40:35 -070014021 JSON_CATCH (out_of_range&)
Ed Tanous3dac7492017-08-02 13:46:20 -070014022 {
14023 // ignore out of range errors: success remains false
14024 }
14025
14026 // throw an exception if test fails
Ed Tanousba9f9a62017-10-11 16:40:35 -070014027 if (JSON_UNLIKELY(not success))
Ed Tanous3dac7492017-08-02 13:46:20 -070014028 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070014029 JSON_THROW(other_error::create(501, "unsuccessful: " + val.dump()));
Ed Tanous3dac7492017-08-02 13:46:20 -070014030 }
14031
14032 break;
14033 }
14034
14035 case patch_operations::invalid:
14036 {
14037 // op must be "add", "remove", "replace", "move", "copy", or
14038 // "test"
Ed Tanousba9f9a62017-10-11 16:40:35 -070014039 JSON_THROW(parse_error::create(105, 0, "operation value '" + op + "' is invalid"));
Ed Tanous3dac7492017-08-02 13:46:20 -070014040 }
14041 }
14042 }
14043
14044 return result;
14045 }
14046
14047 /*!
14048 @brief creates a diff as a JSON patch
14049
14050 Creates a [JSON Patch](http://jsonpatch.com) so that value @a source can
14051 be changed into the value @a target by calling @ref patch function.
14052
14053 @invariant For two JSON values @a source and @a target, the following code
14054 yields always `true`:
14055 @code {.cpp}
14056 source.patch(diff(source, target)) == target;
14057 @endcode
14058
14059 @note Currently, only `remove`, `add`, and `replace` operations are
14060 generated.
14061
14062 @param[in] source JSON value to compare from
14063 @param[in] target JSON value to compare against
14064 @param[in] path helper value to create JSON pointers
14065
14066 @return a JSON patch to convert the @a source to @a target
14067
14068 @complexity Linear in the lengths of @a source and @a target.
14069
14070 @liveexample{The following code shows how a JSON patch is created as a
14071 diff for two JSON values.,diff}
14072
14073 @sa @ref patch -- apply a JSON patch
14074
14075 @sa [RFC 6902 (JSON Patch)](https://tools.ietf.org/html/rfc6902)
14076
14077 @since version 2.0.0
14078 */
Ed Tanousba9f9a62017-10-11 16:40:35 -070014079 static basic_json diff(const basic_json& source, const basic_json& target,
Ed Tanous3dac7492017-08-02 13:46:20 -070014080 const std::string& path = "")
14081 {
14082 // the patch
14083 basic_json result(value_t::array);
14084
14085 // if the values are the same, return empty patch
14086 if (source == target)
14087 {
14088 return result;
14089 }
14090
14091 if (source.type() != target.type())
14092 {
14093 // different types: replace value
14094 result.push_back(
14095 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070014096 {"op", "replace"}, {"path", path}, {"value", target}
Ed Tanous3dac7492017-08-02 13:46:20 -070014097 });
14098 }
14099 else
14100 {
14101 switch (source.type())
14102 {
14103 case value_t::array:
14104 {
14105 // first pass: traverse common elements
Ed Tanousba9f9a62017-10-11 16:40:35 -070014106 std::size_t i = 0;
Ed Tanous3dac7492017-08-02 13:46:20 -070014107 while (i < source.size() and i < target.size())
14108 {
14109 // recursive call to compare array values at index i
14110 auto temp_diff = diff(source[i], target[i], path + "/" + std::to_string(i));
14111 result.insert(result.end(), temp_diff.begin(), temp_diff.end());
14112 ++i;
14113 }
14114
14115 // i now reached the end of at least one array
14116 // in a second pass, traverse the remaining elements
14117
14118 // remove my remaining elements
14119 const auto end_index = static_cast<difference_type>(result.size());
14120 while (i < source.size())
14121 {
14122 // add operations in reverse order to avoid invalid
14123 // indices
14124 result.insert(result.begin() + end_index, object(
14125 {
14126 {"op", "remove"},
14127 {"path", path + "/" + std::to_string(i)}
14128 }));
14129 ++i;
14130 }
14131
14132 // add other remaining elements
14133 while (i < target.size())
14134 {
14135 result.push_back(
14136 {
14137 {"op", "add"},
14138 {"path", path + "/" + std::to_string(i)},
14139 {"value", target[i]}
14140 });
14141 ++i;
14142 }
14143
14144 break;
14145 }
14146
14147 case value_t::object:
14148 {
14149 // first pass: traverse this object's elements
14150 for (auto it = source.begin(); it != source.end(); ++it)
14151 {
14152 // escape the key name to be used in a JSON patch
14153 const auto key = json_pointer::escape(it.key());
14154
14155 if (target.find(it.key()) != target.end())
14156 {
14157 // recursive call to compare object values at key it
14158 auto temp_diff = diff(it.value(), target[it.key()], path + "/" + key);
14159 result.insert(result.end(), temp_diff.begin(), temp_diff.end());
14160 }
14161 else
14162 {
14163 // found a key that is not in o -> remove it
14164 result.push_back(object(
14165 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070014166 {"op", "remove"}, {"path", path + "/" + key}
Ed Tanous3dac7492017-08-02 13:46:20 -070014167 }));
14168 }
14169 }
14170
14171 // second pass: traverse other object's elements
14172 for (auto it = target.begin(); it != target.end(); ++it)
14173 {
14174 if (source.find(it.key()) == source.end())
14175 {
14176 // found a key that is not in this -> add it
14177 const auto key = json_pointer::escape(it.key());
14178 result.push_back(
14179 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070014180 {"op", "add"}, {"path", path + "/" + key},
Ed Tanous3dac7492017-08-02 13:46:20 -070014181 {"value", it.value()}
14182 });
14183 }
14184 }
14185
14186 break;
14187 }
14188
14189 default:
14190 {
14191 // both primitive type: replace value
14192 result.push_back(
14193 {
Ed Tanousba9f9a62017-10-11 16:40:35 -070014194 {"op", "replace"}, {"path", path}, {"value", target}
Ed Tanous3dac7492017-08-02 13:46:20 -070014195 });
14196 break;
14197 }
14198 }
14199 }
14200
14201 return result;
14202 }
14203
14204 /// @}
14205};
14206
14207/////////////
14208// presets //
14209/////////////
14210
14211/*!
14212@brief default JSON class
14213
14214This type is the default specialization of the @ref basic_json class which
14215uses the standard template types.
14216
14217@since version 1.0.0
14218*/
14219using json = basic_json<>;
Ed Tanousba9f9a62017-10-11 16:40:35 -070014220
14221//////////////////
14222// json_pointer //
14223//////////////////
14224
14225NLOHMANN_BASIC_JSON_TPL_DECLARATION
14226NLOHMANN_BASIC_JSON_TPL&
14227json_pointer::get_and_create(NLOHMANN_BASIC_JSON_TPL& j) const
14228{
14229 using size_type = typename NLOHMANN_BASIC_JSON_TPL::size_type;
14230 auto result = &j;
14231
14232 // in case no reference tokens exist, return a reference to the JSON value
14233 // j which will be overwritten by a primitive value
14234 for (const auto& reference_token : reference_tokens)
14235 {
14236 switch (result->m_type)
14237 {
14238 case detail::value_t::null:
14239 {
14240 if (reference_token == "0")
14241 {
14242 // start a new array if reference token is 0
14243 result = &result->operator[](0);
14244 }
14245 else
14246 {
14247 // start a new object otherwise
14248 result = &result->operator[](reference_token);
14249 }
14250 break;
14251 }
14252
14253 case detail::value_t::object:
14254 {
14255 // create an entry in the object
14256 result = &result->operator[](reference_token);
14257 break;
14258 }
14259
14260 case detail::value_t::array:
14261 {
14262 // create an entry in the array
14263 JSON_TRY
14264 {
14265 result = &result->operator[](static_cast<size_type>(std::stoi(reference_token)));
14266 }
14267 JSON_CATCH(std::invalid_argument&)
14268 {
14269 JSON_THROW(detail::parse_error::create(109, 0, "array index '" + reference_token + "' is not a number"));
14270 }
14271 break;
14272 }
14273
14274 /*
14275 The following code is only reached if there exists a reference
14276 token _and_ the current value is primitive. In this case, we have
14277 an error situation, because primitive values may only occur as
14278 single value; that is, with an empty list of reference tokens.
14279 */
14280 default:
14281 JSON_THROW(detail::type_error::create(313, "invalid value to unflatten"));
14282 }
14283 }
14284
14285 return *result;
14286}
14287
14288NLOHMANN_BASIC_JSON_TPL_DECLARATION
14289NLOHMANN_BASIC_JSON_TPL&
14290json_pointer::get_unchecked(NLOHMANN_BASIC_JSON_TPL* ptr) const
14291{
14292 using size_type = typename NLOHMANN_BASIC_JSON_TPL::size_type;
14293 for (const auto& reference_token : reference_tokens)
14294 {
14295 // convert null values to arrays or objects before continuing
14296 if (ptr->m_type == detail::value_t::null)
14297 {
14298 // check if reference token is a number
14299 const bool nums =
14300 std::all_of(reference_token.begin(), reference_token.end(),
14301 [](const char x)
14302 {
14303 return (x >= '0' and x <= '9');
14304 });
14305
14306 // change value to array for numbers or "-" or to object otherwise
14307 *ptr = (nums or reference_token == "-")
14308 ? detail::value_t::array
14309 : detail::value_t::object;
14310 }
14311
14312 switch (ptr->m_type)
14313 {
14314 case detail::value_t::object:
14315 {
14316 // use unchecked object access
14317 ptr = &ptr->operator[](reference_token);
14318 break;
14319 }
14320
14321 case detail::value_t::array:
14322 {
14323 // error condition (cf. RFC 6901, Sect. 4)
14324 if (JSON_UNLIKELY(reference_token.size() > 1 and reference_token[0] == '0'))
14325 {
14326 JSON_THROW(detail::parse_error::create(106, 0,
14327 "array index '" + reference_token +
14328 "' must not begin with '0'"));
14329 }
14330
14331 if (reference_token == "-")
14332 {
14333 // explicitly treat "-" as index beyond the end
14334 ptr = &ptr->operator[](ptr->m_value.array->size());
14335 }
14336 else
14337 {
14338 // convert array index to number; unchecked access
14339 JSON_TRY
14340 {
14341 ptr = &ptr->operator[](
14342 static_cast<size_type>(std::stoi(reference_token)));
14343 }
14344 JSON_CATCH(std::invalid_argument&)
14345 {
14346 JSON_THROW(detail::parse_error::create(109, 0, "array index '" + reference_token + "' is not a number"));
14347 }
14348 }
14349 break;
14350 }
14351
14352 default:
14353 JSON_THROW(detail::out_of_range::create(404, "unresolved reference token '" + reference_token + "'"));
14354 }
14355 }
14356
14357 return *ptr;
14358}
14359
14360NLOHMANN_BASIC_JSON_TPL_DECLARATION
14361NLOHMANN_BASIC_JSON_TPL&
14362json_pointer::get_checked(NLOHMANN_BASIC_JSON_TPL* ptr) const
14363{
14364 using size_type = typename NLOHMANN_BASIC_JSON_TPL::size_type;
14365 for (const auto& reference_token : reference_tokens)
14366 {
14367 switch (ptr->m_type)
14368 {
14369 case detail::value_t::object:
14370 {
14371 // note: at performs range check
14372 ptr = &ptr->at(reference_token);
14373 break;
14374 }
14375
14376 case detail::value_t::array:
14377 {
14378 if (JSON_UNLIKELY(reference_token == "-"))
14379 {
14380 // "-" always fails the range check
14381 JSON_THROW(detail::out_of_range::create(402,
14382 "array index '-' (" + std::to_string(ptr->m_value.array->size()) +
14383 ") is out of range"));
14384 }
14385
14386 // error condition (cf. RFC 6901, Sect. 4)
14387 if (JSON_UNLIKELY(reference_token.size() > 1 and reference_token[0] == '0'))
14388 {
14389 JSON_THROW(detail::parse_error::create(106, 0,
14390 "array index '" + reference_token +
14391 "' must not begin with '0'"));
14392 }
14393
14394 // note: at performs range check
14395 JSON_TRY
14396 {
14397 ptr = &ptr->at(static_cast<size_type>(std::stoi(reference_token)));
14398 }
14399 JSON_CATCH(std::invalid_argument&)
14400 {
14401 JSON_THROW(detail::parse_error::create(109, 0, "array index '" + reference_token + "' is not a number"));
14402 }
14403 break;
14404 }
14405
14406 default:
14407 JSON_THROW(detail::out_of_range::create(404, "unresolved reference token '" + reference_token + "'"));
14408 }
14409 }
14410
14411 return *ptr;
14412}
14413
14414NLOHMANN_BASIC_JSON_TPL_DECLARATION
14415const NLOHMANN_BASIC_JSON_TPL&
14416json_pointer::get_unchecked(const NLOHMANN_BASIC_JSON_TPL* ptr) const
14417{
14418 using size_type = typename NLOHMANN_BASIC_JSON_TPL::size_type;
14419 for (const auto& reference_token : reference_tokens)
14420 {
14421 switch (ptr->m_type)
14422 {
14423 case detail::value_t::object:
14424 {
14425 // use unchecked object access
14426 ptr = &ptr->operator[](reference_token);
14427 break;
14428 }
14429
14430 case detail::value_t::array:
14431 {
14432 if (JSON_UNLIKELY(reference_token == "-"))
14433 {
14434 // "-" cannot be used for const access
14435 JSON_THROW(detail::out_of_range::create(402,
14436 "array index '-' (" + std::to_string(ptr->m_value.array->size()) +
14437 ") is out of range"));
14438 }
14439
14440 // error condition (cf. RFC 6901, Sect. 4)
14441 if (JSON_UNLIKELY(reference_token.size() > 1 and reference_token[0] == '0'))
14442 {
14443 JSON_THROW(detail::parse_error::create(106, 0,
14444 "array index '" + reference_token +
14445 "' must not begin with '0'"));
14446 }
14447
14448 // use unchecked array access
14449 JSON_TRY
14450 {
14451 ptr = &ptr->operator[](
14452 static_cast<size_type>(std::stoi(reference_token)));
14453 }
14454 JSON_CATCH(std::invalid_argument&)
14455 {
14456 JSON_THROW(detail::parse_error::create(109, 0, "array index '" + reference_token + "' is not a number"));
14457 }
14458 break;
14459 }
14460
14461 default:
14462 JSON_THROW(detail::out_of_range::create(404, "unresolved reference token '" + reference_token + "'"));
14463 }
14464 }
14465
14466 return *ptr;
14467}
14468
14469NLOHMANN_BASIC_JSON_TPL_DECLARATION
14470const NLOHMANN_BASIC_JSON_TPL&
14471json_pointer::get_checked(const NLOHMANN_BASIC_JSON_TPL* ptr) const
14472{
14473 using size_type = typename NLOHMANN_BASIC_JSON_TPL::size_type;
14474 for (const auto& reference_token : reference_tokens)
14475 {
14476 switch (ptr->m_type)
14477 {
14478 case detail::value_t::object:
14479 {
14480 // note: at performs range check
14481 ptr = &ptr->at(reference_token);
14482 break;
14483 }
14484
14485 case detail::value_t::array:
14486 {
14487 if (JSON_UNLIKELY(reference_token == "-"))
14488 {
14489 // "-" always fails the range check
14490 JSON_THROW(detail::out_of_range::create(402,
14491 "array index '-' (" + std::to_string(ptr->m_value.array->size()) +
14492 ") is out of range"));
14493 }
14494
14495 // error condition (cf. RFC 6901, Sect. 4)
14496 if (JSON_UNLIKELY(reference_token.size() > 1 and reference_token[0] == '0'))
14497 {
14498 JSON_THROW(detail::parse_error::create(106, 0,
14499 "array index '" + reference_token +
14500 "' must not begin with '0'"));
14501 }
14502
14503 // note: at performs range check
14504 JSON_TRY
14505 {
14506 ptr = &ptr->at(static_cast<size_type>(std::stoi(reference_token)));
14507 }
14508 JSON_CATCH(std::invalid_argument&)
14509 {
14510 JSON_THROW(detail::parse_error::create(109, 0, "array index '" + reference_token + "' is not a number"));
14511 }
14512 break;
14513 }
14514
14515 default:
14516 JSON_THROW(detail::out_of_range::create(404, "unresolved reference token '" + reference_token + "'"));
14517 }
14518 }
14519
14520 return *ptr;
14521}
14522
14523NLOHMANN_BASIC_JSON_TPL_DECLARATION
14524void json_pointer::flatten(const std::string& reference_string,
14525 const NLOHMANN_BASIC_JSON_TPL& value,
14526 NLOHMANN_BASIC_JSON_TPL& result)
14527{
14528 switch (value.m_type)
14529 {
14530 case detail::value_t::array:
14531 {
14532 if (value.m_value.array->empty())
14533 {
14534 // flatten empty array as null
14535 result[reference_string] = nullptr;
14536 }
14537 else
14538 {
14539 // iterate array and use index as reference string
14540 for (std::size_t i = 0; i < value.m_value.array->size(); ++i)
14541 {
14542 flatten(reference_string + "/" + std::to_string(i),
14543 value.m_value.array->operator[](i), result);
14544 }
14545 }
14546 break;
14547 }
14548
14549 case detail::value_t::object:
14550 {
14551 if (value.m_value.object->empty())
14552 {
14553 // flatten empty object as null
14554 result[reference_string] = nullptr;
14555 }
14556 else
14557 {
14558 // iterate object and use keys as reference string
14559 for (const auto& element : *value.m_value.object)
14560 {
14561 flatten(reference_string + "/" + escape(element.first), element.second, result);
14562 }
14563 }
14564 break;
14565 }
14566
14567 default:
14568 {
14569 // add primitive value with its reference string
14570 result[reference_string] = value;
14571 break;
14572 }
14573 }
14574}
14575
14576NLOHMANN_BASIC_JSON_TPL_DECLARATION
14577NLOHMANN_BASIC_JSON_TPL
14578json_pointer::unflatten(const NLOHMANN_BASIC_JSON_TPL& value)
14579{
14580 if (JSON_UNLIKELY(not value.is_object()))
14581 {
14582 JSON_THROW(detail::type_error::create(314, "only objects can be unflattened"));
14583 }
14584
14585 NLOHMANN_BASIC_JSON_TPL result;
14586
14587 // iterate the JSON object values
14588 for (const auto& element : *value.m_value.object)
14589 {
14590 if (JSON_UNLIKELY(not element.second.is_primitive()))
14591 {
14592 JSON_THROW(detail::type_error::create(315, "values in object must be primitive"));
14593 }
14594
14595 // assign value to reference pointed to by JSON pointer; Note that if
14596 // the JSON pointer is "" (i.e., points to the whole value), function
14597 // get_and_create returns a reference to result itself. An assignment
14598 // will then create a primitive value.
14599 json_pointer(element.first).get_and_create(result) = element.second;
14600 }
14601
14602 return result;
14603}
14604
14605inline bool operator==(json_pointer const& lhs, json_pointer const& rhs) noexcept
14606{
14607 return (lhs.reference_tokens == rhs.reference_tokens);
14608}
14609
14610inline bool operator!=(json_pointer const& lhs, json_pointer const& rhs) noexcept
14611{
14612 return not (lhs == rhs);
14613}
Ed Tanous3dac7492017-08-02 13:46:20 -070014614} // namespace nlohmann
14615
14616
14617///////////////////////
14618// nonmember support //
14619///////////////////////
14620
14621// specialization of std::swap, and std::hash
14622namespace std
14623{
14624/*!
14625@brief exchanges the values of two JSON objects
14626
14627@since version 1.0.0
14628*/
14629template<>
14630inline void swap(nlohmann::json& j1,
14631 nlohmann::json& j2) noexcept(
14632 is_nothrow_move_constructible<nlohmann::json>::value and
14633 is_nothrow_move_assignable<nlohmann::json>::value
14634 )
14635{
14636 j1.swap(j2);
14637}
14638
14639/// hash value for JSON objects
14640template<>
14641struct hash<nlohmann::json>
14642{
14643 /*!
14644 @brief return a hash value for a JSON object
14645
14646 @since version 1.0.0
14647 */
14648 std::size_t operator()(const nlohmann::json& j) const
14649 {
14650 // a naive hashing via the string representation
14651 const auto& h = hash<nlohmann::json::string_t>();
14652 return h(j.dump());
14653 }
14654};
Ed Tanousba9f9a62017-10-11 16:40:35 -070014655
14656/// specialization for std::less<value_t>
14657/// @note: do not remove the space after '<',
14658/// see https://github.com/nlohmann/json/pull/679
14659template<>
14660struct less< ::nlohmann::detail::value_t>
14661{
14662 /*!
14663 @brief compare two value_t enum values
14664 @since version 3.0.0
14665 */
14666 bool operator()(nlohmann::detail::value_t lhs,
14667 nlohmann::detail::value_t rhs) const noexcept
14668 {
14669 return nlohmann::detail::operator<(lhs, rhs);
14670 }
14671};
14672
Ed Tanous3dac7492017-08-02 13:46:20 -070014673} // namespace std
14674
14675/*!
14676@brief user-defined string literal for JSON values
14677
14678This operator implements a user-defined string literal for JSON objects. It
14679can be used by adding `"_json"` to a string literal and returns a JSON object
14680if no parse error occurred.
14681
14682@param[in] s a string representation of a JSON object
14683@param[in] n the length of string @a s
14684@return a JSON object
14685
14686@since version 1.0.0
14687*/
14688inline nlohmann::json operator "" _json(const char* s, std::size_t n)
14689{
14690 return nlohmann::json::parse(s, s + n);
14691}
14692
14693/*!
14694@brief user-defined string literal for JSON pointer
14695
14696This operator implements a user-defined string literal for JSON Pointers. It
14697can be used by adding `"_json_pointer"` to a string literal and returns a JSON pointer
14698object if no parse error occurred.
14699
14700@param[in] s a string representation of a JSON Pointer
14701@param[in] n the length of string @a s
14702@return a JSON pointer object
14703
14704@since version 2.0.0
14705*/
14706inline nlohmann::json::json_pointer operator "" _json_pointer(const char* s, std::size_t n)
14707{
14708 return nlohmann::json::json_pointer(std::string(s, n));
14709}
14710
14711// restore GCC/clang diagnostic settings
14712#if defined(__clang__) || defined(__GNUC__) || defined(__GNUG__)
14713 #pragma GCC diagnostic pop
14714#endif
Ed Tanousba9f9a62017-10-11 16:40:35 -070014715#if defined(__clang__)
14716 #pragma GCC diagnostic pop
14717#endif
Ed Tanous3dac7492017-08-02 13:46:20 -070014718
14719// clean up
14720#undef JSON_CATCH
Ed Tanous3dac7492017-08-02 13:46:20 -070014721#undef JSON_THROW
14722#undef JSON_TRY
Ed Tanousba9f9a62017-10-11 16:40:35 -070014723#undef JSON_LIKELY
14724#undef JSON_UNLIKELY
14725#undef JSON_DEPRECATED
14726#undef NLOHMANN_BASIC_JSON_TPL_DECLARATION
14727#undef NLOHMANN_BASIC_JSON_TPL
Ed Tanous3dac7492017-08-02 13:46:20 -070014728
Ed Tanousba9f9a62017-10-11 16:40:35 -070014729#endif