document.h
浏览该文件的文档.
1 // Tencent is pleased to support the open source community by making RapidJSON available.
2 //
3 // Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved.
4 //
5 // Licensed under the MIT License (the "License"); you may not use this file except
6 // in compliance with the License. You may obtain a copy of the License at
7 //
8 // http://opensource.org/licenses/MIT
9 //
10 // Unless required by applicable law or agreed to in writing, software distributed
11 // under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
12 // CONDITIONS OF ANY KIND, either express or implied. See the License for the
13 // specific language governing permissions and limitations under the License.
14 
15 #ifndef RAPIDJSON_DOCUMENT_H_
16 #define RAPIDJSON_DOCUMENT_H_
17 
18 /*! \file document.h */
19 
20 #include "reader.h"
21 #include "internal/meta.h"
22 #include "internal/strfunc.h"
23 #include "memorystream.h"
24 #include "encodedstream.h"
25 #include <new> // placement new
26 #include <limits>
27 #ifdef __cpp_lib_three_way_comparison
28 #include <compare>
29 #endif
30 
31 RAPIDJSON_DIAG_PUSH
32 #ifdef __clang__
33 RAPIDJSON_DIAG_OFF(padded)
34 RAPIDJSON_DIAG_OFF(switch-enum)
35 RAPIDJSON_DIAG_OFF(c++98-compat)
36 #elif defined(_MSC_VER)
37 RAPIDJSON_DIAG_OFF(4127) // conditional expression is constant
38 RAPIDJSON_DIAG_OFF(4244) // conversion from kXxxFlags to 'uint16_t', possible loss of data
39 #endif
40 
41 #ifdef __GNUC__
42 RAPIDJSON_DIAG_OFF(effc++)
43 #endif // __GNUC__
44 
45 #ifndef RAPIDJSON_NOMEMBERITERATORCLASS
46 #include <iterator> // std::random_access_iterator_tag
47 #endif
48 
49 #if RAPIDJSON_HAS_CXX11_RVALUE_REFS
50 #include <utility> // std::move
51 #endif
52 
53 RAPIDJSON_NAMESPACE_BEGIN
54 
55 // Forward declaration.
56 template <typename Encoding, typename Allocator>
58 
59 template <typename Encoding, typename Allocator, typename StackAllocator>
61 
62 /*! \def RAPIDJSON_DEFAULT_ALLOCATOR
63  \ingroup RAPIDJSON_CONFIG
64  \brief Allows to choose default allocator.
65 
66  User can define this to use CrtAllocator or MemoryPoolAllocator.
67 */
68 #ifndef RAPIDJSON_DEFAULT_ALLOCATOR
69 #define RAPIDJSON_DEFAULT_ALLOCATOR MemoryPoolAllocator<CrtAllocator>
70 #endif
71 
72 /*! \def RAPIDJSON_DEFAULT_STACK_ALLOCATOR
73  \ingroup RAPIDJSON_CONFIG
74  \brief Allows to choose default stack allocator for Document.
75 
76  User can define this to use CrtAllocator or MemoryPoolAllocator.
77 */
78 #ifndef RAPIDJSON_DEFAULT_STACK_ALLOCATOR
79 #define RAPIDJSON_DEFAULT_STACK_ALLOCATOR CrtAllocator
80 #endif
81 
82 /*! \def RAPIDJSON_VALUE_DEFAULT_OBJECT_CAPACITY
83  \ingroup RAPIDJSON_CONFIG
84  \brief User defined kDefaultObjectCapacity value.
85 
86  User can define this as any natural number.
87 */
88 #ifndef RAPIDJSON_VALUE_DEFAULT_OBJECT_CAPACITY
89 // number of objects that rapidjson::Value allocates memory for by default
90 #define RAPIDJSON_VALUE_DEFAULT_OBJECT_CAPACITY 16
91 #endif
92 
93 /*! \def RAPIDJSON_VALUE_DEFAULT_ARRAY_CAPACITY
94  \ingroup RAPIDJSON_CONFIG
95  \brief User defined kDefaultArrayCapacity value.
96 
97  User can define this as any natural number.
98 */
99 #ifndef RAPIDJSON_VALUE_DEFAULT_ARRAY_CAPACITY
100 // number of array elements that rapidjson::Value allocates memory for by default
101 #define RAPIDJSON_VALUE_DEFAULT_ARRAY_CAPACITY 16
102 #endif
103 
104 //! Name-value pair in a JSON object value.
105 /*!
106  This class was internal to GenericValue. It used to be a inner struct.
107  But a compiler (IBM XL C/C++ for AIX) have reported to have problem with that so it moved as a namespace scope struct.
108  https://code.google.com/p/rapidjson/issues/detail?id=64
109 */
110 template <typename Encoding, typename Allocator>
112 public:
113  GenericValue<Encoding, Allocator> name; //!< name of member (must be a string)
115 
116 #if RAPIDJSON_HAS_CXX11_RVALUE_REFS
117  //! Move constructor in C++11
118  GenericMember(GenericMember&& rhs) RAPIDJSON_NOEXCEPT
119  : name(std::move(rhs.name)),
120  value(std::move(rhs.value))
121  {
122  }
123 
124  //! Move assignment in C++11
125  GenericMember& operator=(GenericMember&& rhs) RAPIDJSON_NOEXCEPT {
126  return *this = static_cast<GenericMember&>(rhs);
127  }
128 #endif
129 
130  //! Assignment with move semantics.
131  /*! \param rhs Source of the assignment. Its name and value will become a null value after assignment.
132  */
133  GenericMember& operator=(GenericMember& rhs) RAPIDJSON_NOEXCEPT {
134  if (RAPIDJSON_LIKELY(this != &rhs)) {
135  name = rhs.name;
136  value = rhs.value;
137  }
138  return *this;
139  }
140 
141  // swap() for std::sort() and other potential use in STL.
142  friend inline void swap(GenericMember& a, GenericMember& b) RAPIDJSON_NOEXCEPT {
143  a.name.Swap(b.name);
144  a.value.Swap(b.value);
145  }
146 
147 private:
148  //! Copy constructor is not permitted.
149  GenericMember(const GenericMember& rhs);
150 };
151 
152 ///////////////////////////////////////////////////////////////////////////////
153 // GenericMemberIterator
154 
155 #ifndef RAPIDJSON_NOMEMBERITERATORCLASS
156 
157 //! (Constant) member iterator for a JSON object value
158 /*!
159  \tparam Const Is this a constant iterator?
160  \tparam Encoding Encoding of the value. (Even non-string values need to have the same encoding in a document)
161  \tparam Allocator Allocator type for allocating memory of object, array and string.
162 
163  This class implements a Random Access Iterator for GenericMember elements
164  of a GenericValue, see ISO/IEC 14882:2003(E) C++ standard, 24.1 [lib.iterator.requirements].
165 
166  \note This iterator implementation is mainly intended to avoid implicit
167  conversions from iterator values to \c NULL,
168  e.g. from GenericValue::FindMember.
169 
170  \note Define \c RAPIDJSON_NOMEMBERITERATORCLASS to fall back to a
171  pointer-based implementation, if your platform doesn't provide
172  the C++ <iterator> header.
173 
174  \see GenericMember, GenericValue::MemberIterator, GenericValue::ConstMemberIterator
175  */
176 template <bool Const, typename Encoding, typename Allocator>
178 
179  friend class GenericValue<Encoding,Allocator>;
180  template <bool, typename, typename> friend class GenericMemberIterator;
181 
183  typedef typename internal::MaybeAddConst<Const,PlainType>::Type ValueType;
184 
185 public:
186  //! Iterator type itself
188  //! Constant iterator type
190  //! Non-constant iterator type
192 
193  /** \name std::iterator_traits support */
194  //@{
195  typedef ValueType value_type;
196  typedef ValueType * pointer;
197  typedef ValueType & reference;
198  typedef std::ptrdiff_t difference_type;
199  typedef std::random_access_iterator_tag iterator_category;
200  //@}
201 
202  //! Pointer to (const) GenericMember
203  typedef pointer Pointer;
204  //! Reference to (const) GenericMember
205  typedef reference Reference;
206  //! Signed integer type (e.g. \c ptrdiff_t)
207  typedef difference_type DifferenceType;
208 
209  //! Default constructor (singular value)
210  /*! Creates an iterator pointing to no element.
211  \note All operations, except for comparisons, are undefined on such values.
212  */
213  GenericMemberIterator() : ptr_() {}
214 
215  //! Iterator conversions to more const
216  /*!
217  \param it (Non-const) iterator to copy from
218 
219  Allows the creation of an iterator from another GenericMemberIterator
220  that is "less const". Especially, creating a non-constant iterator
221  from a constant iterator are disabled:
222  \li const -> non-const (not ok)
223  \li const -> const (ok)
224  \li non-const -> const (ok)
225  \li non-const -> non-const (ok)
226 
227  \note If the \c Const template parameter is already \c false, this
228  constructor effectively defines a regular copy-constructor.
229  Otherwise, the copy constructor is implicitly defined.
230  */
231  GenericMemberIterator(const NonConstIterator & it) : ptr_(it.ptr_) {}
232  Iterator& operator=(const NonConstIterator & it) { ptr_ = it.ptr_; return *this; }
233 
234  //! @name stepping
235  //@{
236  Iterator& operator++(){ ++ptr_; return *this; }
237  Iterator& operator--(){ --ptr_; return *this; }
238  Iterator operator++(int){ Iterator old(*this); ++ptr_; return old; }
239  Iterator operator--(int){ Iterator old(*this); --ptr_; return old; }
240  //@}
241 
242  //! @name increment/decrement
243  //@{
244  Iterator operator+(DifferenceType n) const { return Iterator(ptr_+n); }
245  Iterator operator-(DifferenceType n) const { return Iterator(ptr_-n); }
246 
247  Iterator& operator+=(DifferenceType n) { ptr_+=n; return *this; }
248  Iterator& operator-=(DifferenceType n) { ptr_-=n; return *this; }
249  //@}
250 
251  //! @name relations
252  //@{
253  template <bool Const_> bool operator==(const GenericMemberIterator<Const_, Encoding, Allocator>& that) const { return ptr_ == that.ptr_; }
254  template <bool Const_> bool operator!=(const GenericMemberIterator<Const_, Encoding, Allocator>& that) const { return ptr_ != that.ptr_; }
255  template <bool Const_> bool operator<=(const GenericMemberIterator<Const_, Encoding, Allocator>& that) const { return ptr_ <= that.ptr_; }
256  template <bool Const_> bool operator>=(const GenericMemberIterator<Const_, Encoding, Allocator>& that) const { return ptr_ >= that.ptr_; }
257  template <bool Const_> bool operator< (const GenericMemberIterator<Const_, Encoding, Allocator>& that) const { return ptr_ < that.ptr_; }
258  template <bool Const_> bool operator> (const GenericMemberIterator<Const_, Encoding, Allocator>& that) const { return ptr_ > that.ptr_; }
259 
260 #ifdef __cpp_lib_three_way_comparison
261  template <bool Const_> std::strong_ordering operator<=>(const GenericMemberIterator<Const_, Encoding, Allocator>& that) const { return ptr_ <=> that.ptr_; }
262 #endif
263  //@}
264 
265  //! @name dereference
266  //@{
267  Reference operator*() const { return *ptr_; }
268  Pointer operator->() const { return ptr_; }
269  Reference operator[](DifferenceType n) const { return ptr_[n]; }
270  //@}
271 
272  //! Distance
273  DifferenceType operator-(ConstIterator that) const { return ptr_-that.ptr_; }
274 
275 private:
276  //! Internal constructor from plain pointer
277  explicit GenericMemberIterator(Pointer p) : ptr_(p) {}
278 
279  Pointer ptr_; //!< raw pointer
280 };
281 
282 #else // RAPIDJSON_NOMEMBERITERATORCLASS
283 
284 // class-based member iterator implementation disabled, use plain pointers
285 
286 template <bool Const, typename Encoding, typename Allocator>
287 class GenericMemberIterator;
288 
289 //! non-const GenericMemberIterator
290 template <typename Encoding, typename Allocator>
291 class GenericMemberIterator<false,Encoding,Allocator> {
292  //! use plain pointer as iterator type
293  typedef GenericMember<Encoding,Allocator>* Iterator;
294 };
295 //! const GenericMemberIterator
296 template <typename Encoding, typename Allocator>
297 class GenericMemberIterator<true,Encoding,Allocator> {
298  //! use plain const pointer as iterator type
299  typedef const GenericMember<Encoding,Allocator>* Iterator;
300 };
301 
302 #endif // RAPIDJSON_NOMEMBERITERATORCLASS
303 
304 ///////////////////////////////////////////////////////////////////////////////
305 // GenericStringRef
306 
307 //! Reference to a constant string (not taking a copy)
308 /*!
309  \tparam CharType character type of the string
310 
311  This helper class is used to automatically infer constant string
312  references for string literals, especially from \c const \b (!)
313  character arrays.
314 
315  The main use is for creating JSON string values without copying the
316  source string via an \ref Allocator. This requires that the referenced
317  string pointers have a sufficient lifetime, which exceeds the lifetime
318  of the associated GenericValue.
319 
320  \b Example
321  \code
322  Value v("foo"); // ok, no need to copy & calculate length
323  const char foo[] = "foo";
324  v.SetString(foo); // ok
325 
326  const char* bar = foo;
327  // Value x(bar); // not ok, can't rely on bar's lifetime
328  Value x(StringRef(bar)); // lifetime explicitly guaranteed by user
329  Value y(StringRef(bar, 3)); // ok, explicitly pass length
330  \endcode
331 
332  \see StringRef, GenericValue::SetString
333 */
334 template<typename CharType>
336  typedef CharType Ch; //!< character type of the string
337 
338  //! Create string reference from \c const character array
339 #ifndef __clang__ // -Wdocumentation
340  /*!
341  This constructor implicitly creates a constant string reference from
342  a \c const character array. It has better performance than
343  \ref StringRef(const CharType*) by inferring the string \ref length
344  from the array length, and also supports strings containing null
345  characters.
346 
347  \tparam N length of the string, automatically inferred
348 
349  \param str Constant character array, lifetime assumed to be longer
350  than the use of the string in e.g. a GenericValue
351 
352  \post \ref s == str
353 
354  \note Constant complexity.
355  \note There is a hidden, private overload to disallow references to
356  non-const character arrays to be created via this constructor.
357  By this, e.g. function-scope arrays used to be filled via
358  \c snprintf are excluded from consideration.
359  In such cases, the referenced string should be \b copied to the
360  GenericValue instead.
361  */
362 #endif
363  template<SizeType N>
364  GenericStringRef(const CharType (&str)[N]) RAPIDJSON_NOEXCEPT
365  : s(str), length(N-1) {}
366 
367  //! Explicitly create string reference from \c const character pointer
368 #ifndef __clang__ // -Wdocumentation
369  /*!
370  This constructor can be used to \b explicitly create a reference to
371  a constant string pointer.
372 
373  \see StringRef(const CharType*)
374 
375  \param str Constant character pointer, lifetime assumed to be longer
376  than the use of the string in e.g. a GenericValue
377 
378  \post \ref s == str
379 
380  \note There is a hidden, private overload to disallow references to
381  non-const character arrays to be created via this constructor.
382  By this, e.g. function-scope arrays used to be filled via
383  \c snprintf are excluded from consideration.
384  In such cases, the referenced string should be \b copied to the
385  GenericValue instead.
386  */
387 #endif
388  explicit GenericStringRef(const CharType* str)
389  : s(str), length(NotNullStrLen(str)) {}
390 
391  //! Create constant string reference from pointer and length
392 #ifndef __clang__ // -Wdocumentation
393  /*! \param str constant string, lifetime assumed to be longer than the use of the string in e.g. a GenericValue
394  \param len length of the string, excluding the trailing NULL terminator
395 
396  \post \ref s == str && \ref length == len
397  \note Constant complexity.
398  */
399 #endif
400  GenericStringRef(const CharType* str, SizeType len)
401  : s(RAPIDJSON_LIKELY(str) ? str : emptyString), length(len) { RAPIDJSON_ASSERT(str != 0 || len == 0u); }
402 
403  GenericStringRef(const GenericStringRef& rhs) : s(rhs.s), length(rhs.length) {}
404 
405  //! implicit conversion to plain CharType pointer
406  operator const Ch *() const { return s; }
407 
408  const Ch* const s; //!< plain CharType pointer
409  const SizeType length; //!< length of the string (excluding the trailing NULL terminator)
410 
411 private:
412  SizeType NotNullStrLen(const CharType* str) {
413  RAPIDJSON_ASSERT(str != 0);
414  return internal::StrLen(str);
415  }
416 
417  /// Empty string - used when passing in a NULL pointer
418  static const Ch emptyString[];
419 
420  //! Disallow construction from non-const array
421  template<SizeType N>
422  GenericStringRef(CharType (&str)[N]) /* = delete */;
423  //! Copy assignment operator not permitted - immutable type
424  GenericStringRef& operator=(const GenericStringRef& rhs) /* = delete */;
425 };
426 
427 template<typename CharType>
428 const CharType GenericStringRef<CharType>::emptyString[] = { CharType() };
429 
430 //! Mark a character pointer as constant string
431 /*! Mark a plain character pointer as a "string literal". This function
432  can be used to avoid copying a character string to be referenced as a
433  value in a JSON GenericValue object, if the string's lifetime is known
434  to be valid long enough.
435  \tparam CharType Character type of the string
436  \param str Constant string, lifetime assumed to be longer than the use of the string in e.g. a GenericValue
437  \return GenericStringRef string reference object
438  \relatesalso GenericStringRef
439 
440  \see GenericValue::GenericValue(StringRefType), GenericValue::operator=(StringRefType), GenericValue::SetString(StringRefType), GenericValue::PushBack(StringRefType, Allocator&), GenericValue::AddMember
441 */
442 template<typename CharType>
443 inline GenericStringRef<CharType> StringRef(const CharType* str) {
444  return GenericStringRef<CharType>(str);
445 }
446 
447 //! Mark a character pointer as constant string
448 /*! Mark a plain character pointer as a "string literal". This function
449  can be used to avoid copying a character string to be referenced as a
450  value in a JSON GenericValue object, if the string's lifetime is known
451  to be valid long enough.
452 
453  This version has better performance with supplied length, and also
454  supports string containing null characters.
455 
456  \tparam CharType character type of the string
457  \param str Constant string, lifetime assumed to be longer than the use of the string in e.g. a GenericValue
458  \param length The length of source string.
459  \return GenericStringRef string reference object
460  \relatesalso GenericStringRef
461 */
462 template<typename CharType>
463 inline GenericStringRef<CharType> StringRef(const CharType* str, size_t length) {
464  return GenericStringRef<CharType>(str, SizeType(length));
465 }
466 
467 #if RAPIDJSON_HAS_STDSTRING
468 //! Mark a string object as constant string
469 /*! Mark a string object (e.g. \c std::string) as a "string literal".
470  This function can be used to avoid copying a string to be referenced as a
471  value in a JSON GenericValue object, if the string's lifetime is known
472  to be valid long enough.
473 
474  \tparam CharType character type of the string
475  \param str Constant string, lifetime assumed to be longer than the use of the string in e.g. a GenericValue
476  \return GenericStringRef string reference object
477  \relatesalso GenericStringRef
478  \note Requires the definition of the preprocessor symbol \ref RAPIDJSON_HAS_STDSTRING.
479 */
480 template<typename CharType>
481 inline GenericStringRef<CharType> StringRef(const std::basic_string<CharType>& str) {
482  return GenericStringRef<CharType>(str.data(), SizeType(str.size()));
483 }
484 #endif
485 
486 ///////////////////////////////////////////////////////////////////////////////
487 // GenericValue type traits
488 namespace internal {
489 
490 template <typename T, typename Encoding = void, typename Allocator = void>
491 struct IsGenericValueImpl : FalseType {};
492 
493 // select candidates according to nested encoding and allocator types
494 template <typename T> struct IsGenericValueImpl<T, typename Void<typename T::EncodingType>::Type, typename Void<typename T::AllocatorType>::Type>
495  : IsBaseOf<GenericValue<typename T::EncodingType, typename T::AllocatorType>, T>::Type {};
496 
497 // helper to match arbitrary GenericValue instantiations, including derived classes
498 template <typename T> struct IsGenericValue : IsGenericValueImpl<T>::Type {};
499 
500 } // namespace internal
501 
502 ///////////////////////////////////////////////////////////////////////////////
503 // TypeHelper
504 
505 namespace internal {
506 
507 template <typename ValueType, typename T>
508 struct TypeHelper {};
509 
510 template<typename ValueType>
511 struct TypeHelper<ValueType, bool> {
512  static bool Is(const ValueType& v) { return v.IsBool(); }
513  static bool Get(const ValueType& v) { return v.GetBool(); }
514  static ValueType& Set(ValueType& v, bool data) { return v.SetBool(data); }
515  static ValueType& Set(ValueType& v, bool data, typename ValueType::AllocatorType&) { return v.SetBool(data); }
516 };
517 
518 template<typename ValueType>
519 struct TypeHelper<ValueType, int> {
520  static bool Is(const ValueType& v) { return v.IsInt(); }
521  static int Get(const ValueType& v) { return v.GetInt(); }
522  static ValueType& Set(ValueType& v, int data) { return v.SetInt(data); }
523  static ValueType& Set(ValueType& v, int data, typename ValueType::AllocatorType&) { return v.SetInt(data); }
524 };
525 
526 template<typename ValueType>
527 struct TypeHelper<ValueType, unsigned> {
528  static bool Is(const ValueType& v) { return v.IsUint(); }
529  static unsigned Get(const ValueType& v) { return v.GetUint(); }
530  static ValueType& Set(ValueType& v, unsigned data) { return v.SetUint(data); }
531  static ValueType& Set(ValueType& v, unsigned data, typename ValueType::AllocatorType&) { return v.SetUint(data); }
532 };
533 
534 #ifdef _MSC_VER
535 RAPIDJSON_STATIC_ASSERT(sizeof(long) == sizeof(int));
536 template<typename ValueType>
537 struct TypeHelper<ValueType, long> {
538  static bool Is(const ValueType& v) { return v.IsInt(); }
539  static long Get(const ValueType& v) { return v.GetInt(); }
540  static ValueType& Set(ValueType& v, long data) { return v.SetInt(data); }
541  static ValueType& Set(ValueType& v, long data, typename ValueType::AllocatorType&) { return v.SetInt(data); }
542 };
543 
544 RAPIDJSON_STATIC_ASSERT(sizeof(unsigned long) == sizeof(unsigned));
545 template<typename ValueType>
546 struct TypeHelper<ValueType, unsigned long> {
547  static bool Is(const ValueType& v) { return v.IsUint(); }
548  static unsigned long Get(const ValueType& v) { return v.GetUint(); }
549  static ValueType& Set(ValueType& v, unsigned long data) { return v.SetUint(data); }
550  static ValueType& Set(ValueType& v, unsigned long data, typename ValueType::AllocatorType&) { return v.SetUint(data); }
551 };
552 #endif
553 
554 template<typename ValueType>
555 struct TypeHelper<ValueType, int64_t> {
556  static bool Is(const ValueType& v) { return v.IsInt64(); }
557  static int64_t Get(const ValueType& v) { return v.GetInt64(); }
558  static ValueType& Set(ValueType& v, int64_t data) { return v.SetInt64(data); }
559  static ValueType& Set(ValueType& v, int64_t data, typename ValueType::AllocatorType&) { return v.SetInt64(data); }
560 };
561 
562 template<typename ValueType>
563 struct TypeHelper<ValueType, uint64_t> {
564  static bool Is(const ValueType& v) { return v.IsUint64(); }
565  static uint64_t Get(const ValueType& v) { return v.GetUint64(); }
566  static ValueType& Set(ValueType& v, uint64_t data) { return v.SetUint64(data); }
567  static ValueType& Set(ValueType& v, uint64_t data, typename ValueType::AllocatorType&) { return v.SetUint64(data); }
568 };
569 
570 template<typename ValueType>
571 struct TypeHelper<ValueType, double> {
572  static bool Is(const ValueType& v) { return v.IsDouble(); }
573  static double Get(const ValueType& v) { return v.GetDouble(); }
574  static ValueType& Set(ValueType& v, double data) { return v.SetDouble(data); }
575  static ValueType& Set(ValueType& v, double data, typename ValueType::AllocatorType&) { return v.SetDouble(data); }
576 };
577 
578 template<typename ValueType>
579 struct TypeHelper<ValueType, float> {
580  static bool Is(const ValueType& v) { return v.IsFloat(); }
581  static float Get(const ValueType& v) { return v.GetFloat(); }
582  static ValueType& Set(ValueType& v, float data) { return v.SetFloat(data); }
583  static ValueType& Set(ValueType& v, float data, typename ValueType::AllocatorType&) { return v.SetFloat(data); }
584 };
585 
586 template<typename ValueType>
587 struct TypeHelper<ValueType, const typename ValueType::Ch*> {
588  typedef const typename ValueType::Ch* StringType;
589  static bool Is(const ValueType& v) { return v.IsString(); }
590  static StringType Get(const ValueType& v) { return v.GetString(); }
591  static ValueType& Set(ValueType& v, const StringType data) { return v.SetString(typename ValueType::StringRefType(data)); }
592  static ValueType& Set(ValueType& v, const StringType data, typename ValueType::AllocatorType& a) { return v.SetString(data, a); }
593 };
594 
595 #if RAPIDJSON_HAS_STDSTRING
596 template<typename ValueType>
597 struct TypeHelper<ValueType, std::basic_string<typename ValueType::Ch> > {
598  typedef std::basic_string<typename ValueType::Ch> StringType;
599  static bool Is(const ValueType& v) { return v.IsString(); }
600  static StringType Get(const ValueType& v) { return StringType(v.GetString(), v.GetStringLength()); }
601  static ValueType& Set(ValueType& v, const StringType& data, typename ValueType::AllocatorType& a) { return v.SetString(data, a); }
602 };
603 #endif
604 
605 template<typename ValueType>
606 struct TypeHelper<ValueType, typename ValueType::Array> {
607  typedef typename ValueType::Array ArrayType;
608  static bool Is(const ValueType& v) { return v.IsArray(); }
609  static ArrayType Get(ValueType& v) { return v.GetArray(); }
610  static ValueType& Set(ValueType& v, ArrayType data) { return v = data; }
611  static ValueType& Set(ValueType& v, ArrayType data, typename ValueType::AllocatorType&) { return v = data; }
612 };
613 
614 template<typename ValueType>
615 struct TypeHelper<ValueType, typename ValueType::ConstArray> {
616  typedef typename ValueType::ConstArray ArrayType;
617  static bool Is(const ValueType& v) { return v.IsArray(); }
618  static ArrayType Get(const ValueType& v) { return v.GetArray(); }
619 };
620 
621 template<typename ValueType>
622 struct TypeHelper<ValueType, typename ValueType::Object> {
623  typedef typename ValueType::Object ObjectType;
624  static bool Is(const ValueType& v) { return v.IsObject(); }
625  static ObjectType Get(ValueType& v) { return v.GetObject(); }
626  static ValueType& Set(ValueType& v, ObjectType data) { return v = data; }
627  static ValueType& Set(ValueType& v, ObjectType data, typename ValueType::AllocatorType&) { return v = data; }
628 };
629 
630 template<typename ValueType>
631 struct TypeHelper<ValueType, typename ValueType::ConstObject> {
632  typedef typename ValueType::ConstObject ObjectType;
633  static bool Is(const ValueType& v) { return v.IsObject(); }
634  static ObjectType Get(const ValueType& v) { return v.GetObject(); }
635 };
636 
637 } // namespace internal
638 
639 // Forward declarations
640 template <bool, typename> class GenericArray;
641 template <bool, typename> class GenericObject;
642 
643 ///////////////////////////////////////////////////////////////////////////////
644 // GenericValue
645 
646 //! Represents a JSON value. Use Value for UTF8 encoding and default allocator.
647 /*!
648  A JSON value can be one of 7 types. This class is a variant type supporting
649  these types.
650 
651  Use the Value if UTF8 and default allocator
652 
653  \tparam Encoding Encoding of the value. (Even non-string values need to have the same encoding in a document)
654  \tparam Allocator Allocator type for allocating memory of object, array and string.
655 */
656 template <typename Encoding, typename Allocator = RAPIDJSON_DEFAULT_ALLOCATOR >
657 class GenericValue {
658 public:
659  //! Name-value pair in an object.
661  typedef Encoding EncodingType; //!< Encoding type from template parameter.
662  typedef Allocator AllocatorType; //!< Allocator type from template parameter.
663  typedef typename Encoding::Ch Ch; //!< Character type derived from Encoding.
664  typedef GenericStringRef<Ch> StringRefType; //!< Reference to a constant string
665  typedef typename GenericMemberIterator<false,Encoding,Allocator>::Iterator MemberIterator; //!< Member iterator for iterating in object.
666  typedef typename GenericMemberIterator<true,Encoding,Allocator>::Iterator ConstMemberIterator; //!< Constant member iterator for iterating in object.
667  typedef GenericValue* ValueIterator; //!< Value iterator for iterating in array.
668  typedef const GenericValue* ConstValueIterator; //!< Constant value iterator for iterating in array.
669  typedef GenericValue<Encoding, Allocator> ValueType; //!< Value type of itself.
674 
675  //!@name Constructors and destructor.
676  //@{
677 
678  //! Default constructor creates a null value.
679  GenericValue() RAPIDJSON_NOEXCEPT : data_() { data_.f.flags = kNullFlag; }
680 
681 #if RAPIDJSON_HAS_CXX11_RVALUE_REFS
682  //! Move constructor in C++11
683  GenericValue(GenericValue&& rhs) RAPIDJSON_NOEXCEPT : data_(rhs.data_) {
684  rhs.data_.f.flags = kNullFlag; // give up contents
685  }
686 #endif
687 
688 private:
689  //! Copy constructor is not permitted.
690  GenericValue(const GenericValue& rhs);
691 
692 #if RAPIDJSON_HAS_CXX11_RVALUE_REFS
693  //! Moving from a GenericDocument is not permitted.
694  template <typename StackAllocator>
695  GenericValue(GenericDocument<Encoding,Allocator,StackAllocator>&& rhs);
696 
697  //! Move assignment from a GenericDocument is not permitted.
698  template <typename StackAllocator>
699  GenericValue& operator=(GenericDocument<Encoding,Allocator,StackAllocator>&& rhs);
700 #endif
701 
702 public:
703 
704  //! Constructor with JSON value type.
705  /*! This creates a Value of specified type with default content.
706  \param type Type of the value.
707  \note Default content for number is zero.
708  */
709  explicit GenericValue(Type type) RAPIDJSON_NOEXCEPT : data_() {
710  static const uint16_t defaultFlags[] = {
711  kNullFlag, kFalseFlag, kTrueFlag, kObjectFlag, kArrayFlag, kShortStringFlag,
712  kNumberAnyFlag
713  };
714  RAPIDJSON_NOEXCEPT_ASSERT(type >= kNullType && type <= kNumberType);
715  data_.f.flags = defaultFlags[type];
716 
717  // Use ShortString to store empty string.
718  if (type == kStringType)
719  data_.ss.SetLength(0);
720  }
721 
722  //! Explicit copy constructor (with allocator)
723  /*! Creates a copy of a Value by using the given Allocator
724  \tparam SourceAllocator allocator of \c rhs
725  \param rhs Value to copy from (read-only)
726  \param allocator Allocator for allocating copied elements and buffers. Commonly use GenericDocument::GetAllocator().
727  \param copyConstStrings Force copying of constant strings (e.g. referencing an in-situ buffer)
728  \see CopyFrom()
729  */
730  template <typename SourceAllocator>
731  GenericValue(const GenericValue<Encoding,SourceAllocator>& rhs, Allocator& allocator, bool copyConstStrings = false) {
732  switch (rhs.GetType()) {
733  case kObjectType: {
734  SizeType count = rhs.data_.o.size;
735  Member* lm = reinterpret_cast<Member*>(allocator.Malloc(count * sizeof(Member)));
736  const typename GenericValue<Encoding,SourceAllocator>::Member* rm = rhs.GetMembersPointer();
737  for (SizeType i = 0; i < count; i++) {
738  new (&lm[i].name) GenericValue(rm[i].name, allocator, copyConstStrings);
739  new (&lm[i].value) GenericValue(rm[i].value, allocator, copyConstStrings);
740  }
741  data_.f.flags = kObjectFlag;
742  data_.o.size = data_.o.capacity = count;
743  SetMembersPointer(lm);
744  }
745  break;
746  case kArrayType: {
747  SizeType count = rhs.data_.a.size;
748  GenericValue* le = reinterpret_cast<GenericValue*>(allocator.Malloc(count * sizeof(GenericValue)));
749  const GenericValue<Encoding,SourceAllocator>* re = rhs.GetElementsPointer();
750  for (SizeType i = 0; i < count; i++)
751  new (&le[i]) GenericValue(re[i], allocator, copyConstStrings);
752  data_.f.flags = kArrayFlag;
753  data_.a.size = data_.a.capacity = count;
754  SetElementsPointer(le);
755  }
756  break;
757  case kStringType:
758  if (rhs.data_.f.flags == kConstStringFlag && !copyConstStrings) {
759  data_.f.flags = rhs.data_.f.flags;
760  data_ = *reinterpret_cast<const Data*>(&rhs.data_);
761  }
762  else
763  SetStringRaw(StringRef(rhs.GetString(), rhs.GetStringLength()), allocator);
764  break;
765  default:
766  data_.f.flags = rhs.data_.f.flags;
767  data_ = *reinterpret_cast<const Data*>(&rhs.data_);
768  break;
769  }
770  }
771 
772  //! Constructor for boolean value.
773  /*! \param b Boolean value
774  \note This constructor is limited to \em real boolean values and rejects
775  implicitly converted types like arbitrary pointers. Use an explicit cast
776  to \c bool, if you want to construct a boolean JSON value in such cases.
777  */
778 #ifndef RAPIDJSON_DOXYGEN_RUNNING // hide SFINAE from Doxygen
779  template <typename T>
780  explicit GenericValue(T b, RAPIDJSON_ENABLEIF((internal::IsSame<bool, T>))) RAPIDJSON_NOEXCEPT // See #472
781 #else
782  explicit GenericValue(bool b) RAPIDJSON_NOEXCEPT
783 #endif
784  : data_() {
785  // safe-guard against failing SFINAE
787  data_.f.flags = b ? kTrueFlag : kFalseFlag;
788  }
789 
790  //! Constructor for int value.
791  explicit GenericValue(int i) RAPIDJSON_NOEXCEPT : data_() {
792  data_.n.i64 = i;
793  data_.f.flags = (i >= 0) ? (kNumberIntFlag | kUintFlag | kUint64Flag) : kNumberIntFlag;
794  }
795 
796  //! Constructor for unsigned value.
797  explicit GenericValue(unsigned u) RAPIDJSON_NOEXCEPT : data_() {
798  data_.n.u64 = u;
799  data_.f.flags = (u & 0x80000000) ? kNumberUintFlag : (kNumberUintFlag | kIntFlag | kInt64Flag);
800  }
801 
802  //! Constructor for int64_t value.
803  explicit GenericValue(int64_t i64) RAPIDJSON_NOEXCEPT : data_() {
804  data_.n.i64 = i64;
805  data_.f.flags = kNumberInt64Flag;
806  if (i64 >= 0) {
807  data_.f.flags |= kNumberUint64Flag;
808  if (!(static_cast<uint64_t>(i64) & RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x00000000)))
809  data_.f.flags |= kUintFlag;
810  if (!(static_cast<uint64_t>(i64) & RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x80000000)))
811  data_.f.flags |= kIntFlag;
812  }
813  else if (i64 >= static_cast<int64_t>(RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x80000000)))
814  data_.f.flags |= kIntFlag;
815  }
816 
817  //! Constructor for uint64_t value.
818  explicit GenericValue(uint64_t u64) RAPIDJSON_NOEXCEPT : data_() {
819  data_.n.u64 = u64;
820  data_.f.flags = kNumberUint64Flag;
821  if (!(u64 & RAPIDJSON_UINT64_C2(0x80000000, 0x00000000)))
822  data_.f.flags |= kInt64Flag;
823  if (!(u64 & RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x00000000)))
824  data_.f.flags |= kUintFlag;
825  if (!(u64 & RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x80000000)))
826  data_.f.flags |= kIntFlag;
827  }
828 
829  //! Constructor for double value.
830  explicit GenericValue(double d) RAPIDJSON_NOEXCEPT : data_() { data_.n.d = d; data_.f.flags = kNumberDoubleFlag; }
831 
832  //! Constructor for float value.
833  explicit GenericValue(float f) RAPIDJSON_NOEXCEPT : data_() { data_.n.d = static_cast<double>(f); data_.f.flags = kNumberDoubleFlag; }
834 
835  //! Constructor for constant string (i.e. do not make a copy of string)
836  GenericValue(const Ch* s, SizeType length) RAPIDJSON_NOEXCEPT : data_() { SetStringRaw(StringRef(s, length)); }
837 
838  //! Constructor for constant string (i.e. do not make a copy of string)
839  explicit GenericValue(StringRefType s) RAPIDJSON_NOEXCEPT : data_() { SetStringRaw(s); }
840 
841  //! Constructor for copy-string (i.e. do make a copy of string)
842  GenericValue(const Ch* s, SizeType length, Allocator& allocator) : data_() { SetStringRaw(StringRef(s, length), allocator); }
843 
844  //! Constructor for copy-string (i.e. do make a copy of string)
845  GenericValue(const Ch*s, Allocator& allocator) : data_() { SetStringRaw(StringRef(s), allocator); }
846 
847 #if RAPIDJSON_HAS_STDSTRING
848  //! Constructor for copy-string from a string object (i.e. do make a copy of string)
849  /*! \note Requires the definition of the preprocessor symbol \ref RAPIDJSON_HAS_STDSTRING.
850  */
851  GenericValue(const std::basic_string<Ch>& s, Allocator& allocator) : data_() { SetStringRaw(StringRef(s), allocator); }
852 #endif
853 
854  //! Constructor for Array.
855  /*!
856  \param a An array obtained by \c GetArray().
857  \note \c Array is always pass-by-value.
858  \note the source array is moved into this value and the sourec array becomes empty.
859  */
860  GenericValue(Array a) RAPIDJSON_NOEXCEPT : data_(a.value_.data_) {
861  a.value_.data_ = Data();
862  a.value_.data_.f.flags = kArrayFlag;
863  }
864 
865  //! Constructor for Object.
866  /*!
867  \param o An object obtained by \c GetObject().
868  \note \c Object is always pass-by-value.
869  \note the source object is moved into this value and the sourec object becomes empty.
870  */
871  GenericValue(Object o) RAPIDJSON_NOEXCEPT : data_(o.value_.data_) {
872  o.value_.data_ = Data();
873  o.value_.data_.f.flags = kObjectFlag;
874  }
875 
876  //! Destructor.
877  /*! Need to destruct elements of array, members of object, or copy-string.
878  */
880  if (Allocator::kNeedFree) { // Shortcut by Allocator's trait
881  switch(data_.f.flags) {
882  case kArrayFlag:
883  {
884  GenericValue* e = GetElementsPointer();
885  for (GenericValue* v = e; v != e + data_.a.size; ++v)
886  v->~GenericValue();
887  Allocator::Free(e);
888  }
889  break;
890 
891  case kObjectFlag:
892  for (MemberIterator m = MemberBegin(); m != MemberEnd(); ++m)
893  m->~Member();
894  Allocator::Free(GetMembersPointer());
895  break;
896 
897  case kCopyStringFlag:
898  Allocator::Free(const_cast<Ch*>(GetStringPointer()));
899  break;
900 
901  default:
902  break; // Do nothing for other types.
903  }
904  }
905  }
906 
907  //@}
908 
909  //!@name Assignment operators
910  //@{
911 
912  //! Assignment with move semantics.
913  /*! \param rhs Source of the assignment. It will become a null value after assignment.
914  */
915  GenericValue& operator=(GenericValue& rhs) RAPIDJSON_NOEXCEPT {
916  if (RAPIDJSON_LIKELY(this != &rhs)) {
917  this->~GenericValue();
918  RawAssign(rhs);
919  }
920  return *this;
921  }
922 
923 #if RAPIDJSON_HAS_CXX11_RVALUE_REFS
924  //! Move assignment in C++11
925  GenericValue& operator=(GenericValue&& rhs) RAPIDJSON_NOEXCEPT {
926  return *this = rhs.Move();
927  }
928 #endif
929 
930  //! Assignment of constant string reference (no copy)
931  /*! \param str Constant string reference to be assigned
932  \note This overload is needed to avoid clashes with the generic primitive type assignment overload below.
933  \see GenericStringRef, operator=(T)
934  */
935  GenericValue& operator=(StringRefType str) RAPIDJSON_NOEXCEPT {
936  GenericValue s(str);
937  return *this = s;
938  }
939 
940  //! Assignment with primitive types.
941  /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t
942  \param value The value to be assigned.
943 
944  \note The source type \c T explicitly disallows all pointer types,
945  especially (\c const) \ref Ch*. This helps avoiding implicitly
946  referencing character strings with insufficient lifetime, use
947  \ref SetString(const Ch*, Allocator&) (for copying) or
948  \ref StringRef() (to explicitly mark the pointer as constant) instead.
949  All other pointer types would implicitly convert to \c bool,
950  use \ref SetBool() instead.
951  */
952  template <typename T>
953  RAPIDJSON_DISABLEIF_RETURN((internal::IsPointer<T>), (GenericValue&))
954  operator=(T value) {
955  GenericValue v(value);
956  return *this = v;
957  }
958 
959  //! Deep-copy assignment from Value
960  /*! Assigns a \b copy of the Value to the current Value object
961  \tparam SourceAllocator Allocator type of \c rhs
962  \param rhs Value to copy from (read-only)
963  \param allocator Allocator to use for copying
964  \param copyConstStrings Force copying of constant strings (e.g. referencing an in-situ buffer)
965  */
966  template <typename SourceAllocator>
967  GenericValue& CopyFrom(const GenericValue<Encoding, SourceAllocator>& rhs, Allocator& allocator, bool copyConstStrings = false) {
968  RAPIDJSON_ASSERT(static_cast<void*>(this) != static_cast<void const*>(&rhs));
969  this->~GenericValue();
970  new (this) GenericValue(rhs, allocator, copyConstStrings);
971  return *this;
972  }
973 
974  //! Exchange the contents of this value with those of other.
975  /*!
976  \param other Another value.
977  \note Constant complexity.
978  */
979  GenericValue& Swap(GenericValue& other) RAPIDJSON_NOEXCEPT {
980  GenericValue temp;
981  temp.RawAssign(*this);
982  RawAssign(other);
983  other.RawAssign(temp);
984  return *this;
985  }
986 
987  //! free-standing swap function helper
988  /*!
989  Helper function to enable support for common swap implementation pattern based on \c std::swap:
990  \code
991  void swap(MyClass& a, MyClass& b) {
992  using std::swap;
993  swap(a.value, b.value);
994  // ...
995  }
996  \endcode
997  \see Swap()
998  */
999  friend inline void swap(GenericValue& a, GenericValue& b) RAPIDJSON_NOEXCEPT { a.Swap(b); }
1000 
1001  //! Prepare Value for move semantics
1002  /*! \return *this */
1003  GenericValue& Move() RAPIDJSON_NOEXCEPT { return *this; }
1004  //@}
1005 
1006  //!@name Equal-to and not-equal-to operators
1007  //@{
1008  //! Equal-to operator
1009  /*!
1010  \note If an object contains duplicated named member, comparing equality with any object is always \c false.
1011  \note Complexity is quadratic in Object's member number and linear for the rest (number of all values in the subtree and total lengths of all strings).
1012  */
1013  template <typename SourceAllocator>
1014  bool operator==(const GenericValue<Encoding, SourceAllocator>& rhs) const {
1015  typedef GenericValue<Encoding, SourceAllocator> RhsType;
1016  if (GetType() != rhs.GetType())
1017  return false;
1018 
1019  switch (GetType()) {
1020  case kObjectType: // Warning: O(n^2) inner-loop
1021  if (data_.o.size != rhs.data_.o.size)
1022  return false;
1023  for (ConstMemberIterator lhsMemberItr = MemberBegin(); lhsMemberItr != MemberEnd(); ++lhsMemberItr) {
1024  typename RhsType::ConstMemberIterator rhsMemberItr = rhs.FindMember(lhsMemberItr->name);
1025  if (rhsMemberItr == rhs.MemberEnd() || lhsMemberItr->value != rhsMemberItr->value)
1026  return false;
1027  }
1028  return true;
1029 
1030  case kArrayType:
1031  if (data_.a.size != rhs.data_.a.size)
1032  return false;
1033  for (SizeType i = 0; i < data_.a.size; i++)
1034  if ((*this)[i] != rhs[i])
1035  return false;
1036  return true;
1037 
1038  case kStringType:
1039  return StringEqual(rhs);
1040 
1041  case kNumberType:
1042  if (IsDouble() || rhs.IsDouble()) {
1043  double a = GetDouble(); // May convert from integer to double.
1044  double b = rhs.GetDouble(); // Ditto
1045  return a >= b && a <= b; // Prevent -Wfloat-equal
1046  }
1047  else
1048  return data_.n.u64 == rhs.data_.n.u64;
1049 
1050  default:
1051  return true;
1052  }
1053  }
1054 
1055  //! Equal-to operator with const C-string pointer
1056  bool operator==(const Ch* rhs) const { return *this == GenericValue(StringRef(rhs)); }
1057 
1058 #if RAPIDJSON_HAS_STDSTRING
1059  //! Equal-to operator with string object
1060  /*! \note Requires the definition of the preprocessor symbol \ref RAPIDJSON_HAS_STDSTRING.
1061  */
1062  bool operator==(const std::basic_string<Ch>& rhs) const { return *this == GenericValue(StringRef(rhs)); }
1063 #endif
1064 
1065  //! Equal-to operator with primitive types
1066  /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t, \c double, \c true, \c false
1067  */
1068  template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>,internal::IsGenericValue<T> >), (bool)) operator==(const T& rhs) const { return *this == GenericValue(rhs); }
1069 
1070  //! Not-equal-to operator
1071  /*! \return !(*this == rhs)
1072  */
1073  template <typename SourceAllocator>
1074  bool operator!=(const GenericValue<Encoding, SourceAllocator>& rhs) const { return !(*this == rhs); }
1075 
1076  //! Not-equal-to operator with const C-string pointer
1077  bool operator!=(const Ch* rhs) const { return !(*this == rhs); }
1078 
1079  //! Not-equal-to operator with arbitrary types
1080  /*! \return !(*this == rhs)
1081  */
1082  template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::IsGenericValue<T>), (bool)) operator!=(const T& rhs) const { return !(*this == rhs); }
1083 
1084  //! Equal-to operator with arbitrary types (symmetric version)
1085  /*! \return (rhs == lhs)
1086  */
1087  template <typename T> friend RAPIDJSON_DISABLEIF_RETURN((internal::IsGenericValue<T>), (bool)) operator==(const T& lhs, const GenericValue& rhs) { return rhs == lhs; }
1088 
1089  //! Not-Equal-to operator with arbitrary types (symmetric version)
1090  /*! \return !(rhs == lhs)
1091  */
1092  template <typename T> friend RAPIDJSON_DISABLEIF_RETURN((internal::IsGenericValue<T>), (bool)) operator!=(const T& lhs, const GenericValue& rhs) { return !(rhs == lhs); }
1093  //@}
1094 
1095  //!@name Type
1096  //@{
1097 
1098  Type GetType() const { return static_cast<Type>(data_.f.flags & kTypeMask); }
1099  bool IsNull() const { return data_.f.flags == kNullFlag; }
1100  bool IsFalse() const { return data_.f.flags == kFalseFlag; }
1101  bool IsTrue() const { return data_.f.flags == kTrueFlag; }
1102  bool IsBool() const { return (data_.f.flags & kBoolFlag) != 0; }
1103  bool IsObject() const { return data_.f.flags == kObjectFlag; }
1104  bool IsArray() const { return data_.f.flags == kArrayFlag; }
1105  bool IsNumber() const { return (data_.f.flags & kNumberFlag) != 0; }
1106  bool IsInt() const { return (data_.f.flags & kIntFlag) != 0; }
1107  bool IsUint() const { return (data_.f.flags & kUintFlag) != 0; }
1108  bool IsInt64() const { return (data_.f.flags & kInt64Flag) != 0; }
1109  bool IsUint64() const { return (data_.f.flags & kUint64Flag) != 0; }
1110  bool IsDouble() const { return (data_.f.flags & kDoubleFlag) != 0; }
1111  bool IsString() const { return (data_.f.flags & kStringFlag) != 0; }
1112 
1113  // Checks whether a number can be losslessly converted to a double.
1114  bool IsLosslessDouble() const {
1115  if (!IsNumber()) return false;
1116  if (IsUint64()) {
1117  uint64_t u = GetUint64();
1118  volatile double d = static_cast<double>(u);
1119  return (d >= 0.0)
1120  && (d < static_cast<double>((std::numeric_limits<uint64_t>::max)()))
1121  && (u == static_cast<uint64_t>(d));
1122  }
1123  if (IsInt64()) {
1124  int64_t i = GetInt64();
1125  volatile double d = static_cast<double>(i);
1126  return (d >= static_cast<double>((std::numeric_limits<int64_t>::min)()))
1127  && (d < static_cast<double>((std::numeric_limits<int64_t>::max)()))
1128  && (i == static_cast<int64_t>(d));
1129  }
1130  return true; // double, int, uint are always lossless
1131  }
1132 
1133  // Checks whether a number is a float (possible lossy).
1134  bool IsFloat() const {
1135  if ((data_.f.flags & kDoubleFlag) == 0)
1136  return false;
1137  double d = GetDouble();
1138  return d >= -3.4028234e38 && d <= 3.4028234e38;
1139  }
1140  // Checks whether a number can be losslessly converted to a float.
1141  bool IsLosslessFloat() const {
1142  if (!IsNumber()) return false;
1143  double a = GetDouble();
1144  if (a < static_cast<double>(-(std::numeric_limits<float>::max)())
1145  || a > static_cast<double>((std::numeric_limits<float>::max)()))
1146  return false;
1147  double b = static_cast<double>(static_cast<float>(a));
1148  return a >= b && a <= b; // Prevent -Wfloat-equal
1149  }
1150 
1151  //@}
1152 
1153  //!@name Null
1154  //@{
1155 
1156  GenericValue& SetNull() { this->~GenericValue(); new (this) GenericValue(); return *this; }
1157 
1158  //@}
1159 
1160  //!@name Bool
1161  //@{
1162 
1163  bool GetBool() const { RAPIDJSON_ASSERT(IsBool()); return data_.f.flags == kTrueFlag; }
1164  //!< Set boolean value
1165  /*! \post IsBool() == true */
1166  GenericValue& SetBool(bool b) { this->~GenericValue(); new (this) GenericValue(b); return *this; }
1167 
1168  //@}
1169 
1170  //!@name Object
1171  //@{
1172 
1173  //! Set this value as an empty object.
1174  /*! \post IsObject() == true */
1175  GenericValue& SetObject() { this->~GenericValue(); new (this) GenericValue(kObjectType); return *this; }
1176 
1177  //! Get the number of members in the object.
1178  SizeType MemberCount() const { RAPIDJSON_ASSERT(IsObject()); return data_.o.size; }
1179 
1180  //! Get the capacity of object.
1181  SizeType MemberCapacity() const { RAPIDJSON_ASSERT(IsObject()); return data_.o.capacity; }
1182 
1183  //! Check whether the object is empty.
1184  bool ObjectEmpty() const { RAPIDJSON_ASSERT(IsObject()); return data_.o.size == 0; }
1185 
1186  //! Get a value from an object associated with the name.
1187  /*! \pre IsObject() == true
1188  \tparam T Either \c Ch or \c const \c Ch (template used for disambiguation with \ref operator[](SizeType))
1189  \note In version 0.1x, if the member is not found, this function returns a null value. This makes issue 7.
1190  Since 0.2, if the name is not correct, it will assert.
1191  If user is unsure whether a member exists, user should use HasMember() first.
1192  A better approach is to use FindMember().
1193  \note Linear time complexity.
1194  */
1195  template <typename T>
1196  RAPIDJSON_DISABLEIF_RETURN((internal::NotExpr<internal::IsSame<typename internal::RemoveConst<T>::Type, Ch> >),(GenericValue&)) operator[](T* name) {
1197  GenericValue n(StringRef(name));
1198  return (*this)[n];
1199  }
1200  template <typename T>
1201  RAPIDJSON_DISABLEIF_RETURN((internal::NotExpr<internal::IsSame<typename internal::RemoveConst<T>::Type, Ch> >),(const GenericValue&)) operator[](T* name) const { return const_cast<GenericValue&>(*this)[name]; }
1202 
1203  //! Get a value from an object associated with the name.
1204  /*! \pre IsObject() == true
1205  \tparam SourceAllocator Allocator of the \c name value
1206 
1207  \note Compared to \ref operator[](T*), this version is faster because it does not need a StrLen().
1208  And it can also handle strings with embedded null characters.
1209 
1210  \note Linear time complexity.
1211  */
1212  template <typename SourceAllocator>
1213  GenericValue& operator[](const GenericValue<Encoding, SourceAllocator>& name) {
1214  MemberIterator member = FindMember(name);
1215  if (member != MemberEnd())
1216  return member->value;
1217  else {
1218  RAPIDJSON_ASSERT(false); // see above note
1219 
1220  // This will generate -Wexit-time-destructors in clang
1221  // static GenericValue NullValue;
1222  // return NullValue;
1223 
1224  // Use static buffer and placement-new to prevent destruction
1225  static char buffer[sizeof(GenericValue)];
1226  return *new (buffer) GenericValue();
1227  }
1228  }
1229  template <typename SourceAllocator>
1230  const GenericValue& operator[](const GenericValue<Encoding, SourceAllocator>& name) const { return const_cast<GenericValue&>(*this)[name]; }
1231 
1232 #if RAPIDJSON_HAS_STDSTRING
1233  //! Get a value from an object associated with name (string object).
1234  GenericValue& operator[](const std::basic_string<Ch>& name) { return (*this)[GenericValue(StringRef(name))]; }
1235  const GenericValue& operator[](const std::basic_string<Ch>& name) const { return (*this)[GenericValue(StringRef(name))]; }
1236 #endif
1237 
1238  //! Const member iterator
1239  /*! \pre IsObject() == true */
1240  ConstMemberIterator MemberBegin() const { RAPIDJSON_ASSERT(IsObject()); return ConstMemberIterator(GetMembersPointer()); }
1241  //! Const \em past-the-end member iterator
1242  /*! \pre IsObject() == true */
1243  ConstMemberIterator MemberEnd() const { RAPIDJSON_ASSERT(IsObject()); return ConstMemberIterator(GetMembersPointer() + data_.o.size); }
1244  //! Member iterator
1245  /*! \pre IsObject() == true */
1246  MemberIterator MemberBegin() { RAPIDJSON_ASSERT(IsObject()); return MemberIterator(GetMembersPointer()); }
1247  //! \em Past-the-end member iterator
1248  /*! \pre IsObject() == true */
1249  MemberIterator MemberEnd() { RAPIDJSON_ASSERT(IsObject()); return MemberIterator(GetMembersPointer() + data_.o.size); }
1250 
1251  //! Request the object to have enough capacity to store members.
1252  /*! \param newCapacity The capacity that the object at least need to have.
1253  \param allocator Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
1254  \return The value itself for fluent API.
1255  \note Linear time complexity.
1256  */
1257  GenericValue& MemberReserve(SizeType newCapacity, Allocator &allocator) {
1258  RAPIDJSON_ASSERT(IsObject());
1259  if (newCapacity > data_.o.capacity) {
1260  SetMembersPointer(reinterpret_cast<Member*>(allocator.Realloc(GetMembersPointer(), data_.o.capacity * sizeof(Member), newCapacity * sizeof(Member))));
1261  data_.o.capacity = newCapacity;
1262  }
1263  return *this;
1264  }
1265 
1266  //! Check whether a member exists in the object.
1267  /*!
1268  \param name Member name to be searched.
1269  \pre IsObject() == true
1270  \return Whether a member with that name exists.
1271  \note It is better to use FindMember() directly if you need the obtain the value as well.
1272  \note Linear time complexity.
1273  */
1274  bool HasMember(const Ch* name) const { return FindMember(name) != MemberEnd(); }
1275 
1276 #if RAPIDJSON_HAS_STDSTRING
1277  //! Check whether a member exists in the object with string object.
1278  /*!
1279  \param name Member name to be searched.
1280  \pre IsObject() == true
1281  \return Whether a member with that name exists.
1282  \note It is better to use FindMember() directly if you need the obtain the value as well.
1283  \note Linear time complexity.
1284  */
1285  bool HasMember(const std::basic_string<Ch>& name) const { return FindMember(name) != MemberEnd(); }
1286 #endif
1287 
1288  //! Check whether a member exists in the object with GenericValue name.
1289  /*!
1290  This version is faster because it does not need a StrLen(). It can also handle string with null character.
1291  \param name Member name to be searched.
1292  \pre IsObject() == true
1293  \return Whether a member with that name exists.
1294  \note It is better to use FindMember() directly if you need the obtain the value as well.
1295  \note Linear time complexity.
1296  */
1297  template <typename SourceAllocator>
1298  bool HasMember(const GenericValue<Encoding, SourceAllocator>& name) const { return FindMember(name) != MemberEnd(); }
1299 
1300  //! Find member by name.
1301  /*!
1302  \param name Member name to be searched.
1303  \pre IsObject() == true
1304  \return Iterator to member, if it exists.
1305  Otherwise returns \ref MemberEnd().
1306 
1307  \note Earlier versions of Rapidjson returned a \c NULL pointer, in case
1308  the requested member doesn't exist. For consistency with e.g.
1309  \c std::map, this has been changed to MemberEnd() now.
1310  \note Linear time complexity.
1311  */
1312  MemberIterator FindMember(const Ch* name) {
1313  GenericValue n(StringRef(name));
1314  return FindMember(n);
1315  }
1316 
1317  ConstMemberIterator FindMember(const Ch* name) const { return const_cast<GenericValue&>(*this).FindMember(name); }
1318 
1319  //! Find member by name.
1320  /*!
1321  This version is faster because it does not need a StrLen(). It can also handle string with null character.
1322  \param name Member name to be searched.
1323  \pre IsObject() == true
1324  \return Iterator to member, if it exists.
1325  Otherwise returns \ref MemberEnd().
1326 
1327  \note Earlier versions of Rapidjson returned a \c NULL pointer, in case
1328  the requested member doesn't exist. For consistency with e.g.
1329  \c std::map, this has been changed to MemberEnd() now.
1330  \note Linear time complexity.
1331  */
1332  template <typename SourceAllocator>
1333  MemberIterator FindMember(const GenericValue<Encoding, SourceAllocator>& name) {
1334  RAPIDJSON_ASSERT(IsObject());
1335  RAPIDJSON_ASSERT(name.IsString());
1336  MemberIterator member = MemberBegin();
1337  for ( ; member != MemberEnd(); ++member)
1338  if (name.StringEqual(member->name))
1339  break;
1340  return member;
1341  }
1342  template <typename SourceAllocator> ConstMemberIterator FindMember(const GenericValue<Encoding, SourceAllocator>& name) const { return const_cast<GenericValue&>(*this).FindMember(name); }
1343 
1344 #if RAPIDJSON_HAS_STDSTRING
1345  //! Find member by string object name.
1346  /*!
1347  \param name Member name to be searched.
1348  \pre IsObject() == true
1349  \return Iterator to member, if it exists.
1350  Otherwise returns \ref MemberEnd().
1351  */
1352  MemberIterator FindMember(const std::basic_string<Ch>& name) { return FindMember(GenericValue(StringRef(name))); }
1353  ConstMemberIterator FindMember(const std::basic_string<Ch>& name) const { return FindMember(GenericValue(StringRef(name))); }
1354 #endif
1355 
1356  //! Add a member (name-value pair) to the object.
1357  /*! \param name A string value as name of member.
1358  \param value Value of any type.
1359  \param allocator Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
1360  \return The value itself for fluent API.
1361  \note The ownership of \c name and \c value will be transferred to this object on success.
1362  \pre IsObject() && name.IsString()
1363  \post name.IsNull() && value.IsNull()
1364  \note Amortized Constant time complexity.
1365  */
1366  GenericValue& AddMember(GenericValue& name, GenericValue& value, Allocator& allocator) {
1367  RAPIDJSON_ASSERT(IsObject());
1368  RAPIDJSON_ASSERT(name.IsString());
1369 
1370  ObjectData& o = data_.o;
1371  if (o.size >= o.capacity)
1372  MemberReserve(o.capacity == 0 ? kDefaultObjectCapacity : (o.capacity + (o.capacity + 1) / 2), allocator);
1373  Member* members = GetMembersPointer();
1374  members[o.size].name.RawAssign(name);
1375  members[o.size].value.RawAssign(value);
1376  o.size++;
1377  return *this;
1378  }
1379 
1380  //! Add a constant string value as member (name-value pair) to the object.
1381  /*! \param name A string value as name of member.
1382  \param value constant string reference as value of member.
1383  \param allocator Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
1384  \return The value itself for fluent API.
1385  \pre IsObject()
1386  \note This overload is needed to avoid clashes with the generic primitive type AddMember(GenericValue&,T,Allocator&) overload below.
1387  \note Amortized Constant time complexity.
1388  */
1389  GenericValue& AddMember(GenericValue& name, StringRefType value, Allocator& allocator) {
1390  GenericValue v(value);
1391  return AddMember(name, v, allocator);
1392  }
1393 
1394 #if RAPIDJSON_HAS_STDSTRING
1395  //! Add a string object as member (name-value pair) to the object.
1396  /*! \param name A string value as name of member.
1397  \param value constant string reference as value of member.
1398  \param allocator Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
1399  \return The value itself for fluent API.
1400  \pre IsObject()
1401  \note This overload is needed to avoid clashes with the generic primitive type AddMember(GenericValue&,T,Allocator&) overload below.
1402  \note Amortized Constant time complexity.
1403  */
1404  GenericValue& AddMember(GenericValue& name, std::basic_string<Ch>& value, Allocator& allocator) {
1405  GenericValue v(value, allocator);
1406  return AddMember(name, v, allocator);
1407  }
1408 #endif
1409 
1410  //! Add any primitive value as member (name-value pair) to the object.
1411  /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t
1412  \param name A string value as name of member.
1413  \param value Value of primitive type \c T as value of member
1414  \param allocator Allocator for reallocating memory. Commonly use GenericDocument::GetAllocator().
1415  \return The value itself for fluent API.
1416  \pre IsObject()
1417 
1418  \note The source type \c T explicitly disallows all pointer types,
1419  especially (\c const) \ref Ch*. This helps avoiding implicitly
1420  referencing character strings with insufficient lifetime, use
1421  \ref AddMember(StringRefType, GenericValue&, Allocator&) or \ref
1422  AddMember(StringRefType, StringRefType, Allocator&).
1423  All other pointer types would implicitly convert to \c bool,
1424  use an explicit cast instead, if needed.
1425  \note Amortized Constant time complexity.
1426  */
1427  template <typename T>
1428  RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (GenericValue&))
1429  AddMember(GenericValue& name, T value, Allocator& allocator) {
1430  GenericValue v(value);
1431  return AddMember(name, v, allocator);
1432  }
1433 
1434 #if RAPIDJSON_HAS_CXX11_RVALUE_REFS
1435  GenericValue& AddMember(GenericValue&& name, GenericValue&& value, Allocator& allocator) {
1436  return AddMember(name, value, allocator);
1437  }
1438  GenericValue& AddMember(GenericValue&& name, GenericValue& value, Allocator& allocator) {
1439  return AddMember(name, value, allocator);
1440  }
1441  GenericValue& AddMember(GenericValue& name, GenericValue&& value, Allocator& allocator) {
1442  return AddMember(name, value, allocator);
1443  }
1444  GenericValue& AddMember(StringRefType name, GenericValue&& value, Allocator& allocator) {
1445  GenericValue n(name);
1446  return AddMember(n, value, allocator);
1447  }
1448 #endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS
1449 
1450 
1451  //! Add a member (name-value pair) to the object.
1452  /*! \param name A constant string reference as name of member.
1453  \param value Value of any type.
1454  \param allocator Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
1455  \return The value itself for fluent API.
1456  \note The ownership of \c value will be transferred to this object on success.
1457  \pre IsObject()
1458  \post value.IsNull()
1459  \note Amortized Constant time complexity.
1460  */
1461  GenericValue& AddMember(StringRefType name, GenericValue& value, Allocator& allocator) {
1462  GenericValue n(name);
1463  return AddMember(n, value, allocator);
1464  }
1465 
1466  //! Add a constant string value as member (name-value pair) to the object.
1467  /*! \param name A constant string reference as name of member.
1468  \param value constant string reference as value of member.
1469  \param allocator Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
1470  \return The value itself for fluent API.
1471  \pre IsObject()
1472  \note This overload is needed to avoid clashes with the generic primitive type AddMember(StringRefType,T,Allocator&) overload below.
1473  \note Amortized Constant time complexity.
1474  */
1475  GenericValue& AddMember(StringRefType name, StringRefType value, Allocator& allocator) {
1476  GenericValue v(value);
1477  return AddMember(name, v, allocator);
1478  }
1479 
1480  //! Add any primitive value as member (name-value pair) to the object.
1481  /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t
1482  \param name A constant string reference as name of member.
1483  \param value Value of primitive type \c T as value of member
1484  \param allocator Allocator for reallocating memory. Commonly use GenericDocument::GetAllocator().
1485  \return The value itself for fluent API.
1486  \pre IsObject()
1487 
1488  \note The source type \c T explicitly disallows all pointer types,
1489  especially (\c const) \ref Ch*. This helps avoiding implicitly
1490  referencing character strings with insufficient lifetime, use
1491  \ref AddMember(StringRefType, GenericValue&, Allocator&) or \ref
1492  AddMember(StringRefType, StringRefType, Allocator&).
1493  All other pointer types would implicitly convert to \c bool,
1494  use an explicit cast instead, if needed.
1495  \note Amortized Constant time complexity.
1496  */
1497  template <typename T>
1498  RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (GenericValue&))
1499  AddMember(StringRefType name, T value, Allocator& allocator) {
1500  GenericValue n(name);
1501  return AddMember(n, value, allocator);
1502  }
1503 
1504  //! Remove all members in the object.
1505  /*! This function do not deallocate memory in the object, i.e. the capacity is unchanged.
1506  \note Linear time complexity.
1507  */
1508  void RemoveAllMembers() {
1509  RAPIDJSON_ASSERT(IsObject());
1510  for (MemberIterator m = MemberBegin(); m != MemberEnd(); ++m)
1511  m->~Member();
1512  data_.o.size = 0;
1513  }
1514 
1515  //! Remove a member in object by its name.
1516  /*! \param name Name of member to be removed.
1517  \return Whether the member existed.
1518  \note This function may reorder the object members. Use \ref
1519  EraseMember(ConstMemberIterator) if you need to preserve the
1520  relative order of the remaining members.
1521  \note Linear time complexity.
1522  */
1523  bool RemoveMember(const Ch* name) {
1524  GenericValue n(StringRef(name));
1525  return RemoveMember(n);
1526  }
1527 
1528 #if RAPIDJSON_HAS_STDSTRING
1529  bool RemoveMember(const std::basic_string<Ch>& name) { return RemoveMember(GenericValue(StringRef(name))); }
1530 #endif
1531 
1532  template <typename SourceAllocator>
1533  bool RemoveMember(const GenericValue<Encoding, SourceAllocator>& name) {
1534  MemberIterator m = FindMember(name);
1535  if (m != MemberEnd()) {
1536  RemoveMember(m);
1537  return true;
1538  }
1539  else
1540  return false;
1541  }
1542 
1543  //! Remove a member in object by iterator.
1544  /*! \param m member iterator (obtained by FindMember() or MemberBegin()).
1545  \return the new iterator after removal.
1546  \note This function may reorder the object members. Use \ref
1547  EraseMember(ConstMemberIterator) if you need to preserve the
1548  relative order of the remaining members.
1549  \note Constant time complexity.
1550  */
1551  MemberIterator RemoveMember(MemberIterator m) {
1552  RAPIDJSON_ASSERT(IsObject());
1553  RAPIDJSON_ASSERT(data_.o.size > 0);
1554  RAPIDJSON_ASSERT(GetMembersPointer() != 0);
1555  RAPIDJSON_ASSERT(m >= MemberBegin() && m < MemberEnd());
1556 
1557  MemberIterator last(GetMembersPointer() + (data_.o.size - 1));
1558  if (data_.o.size > 1 && m != last)
1559  *m = *last; // Move the last one to this place
1560  else
1561  m->~Member(); // Only one left, just destroy
1562  --data_.o.size;
1563  return m;
1564  }
1565 
1566  //! Remove a member from an object by iterator.
1567  /*! \param pos iterator to the member to remove
1568  \pre IsObject() == true && \ref MemberBegin() <= \c pos < \ref MemberEnd()
1569  \return Iterator following the removed element.
1570  If the iterator \c pos refers to the last element, the \ref MemberEnd() iterator is returned.
1571  \note This function preserves the relative order of the remaining object
1572  members. If you do not need this, use the more efficient \ref RemoveMember(MemberIterator).
1573  \note Linear time complexity.
1574  */
1575  MemberIterator EraseMember(ConstMemberIterator pos) {
1576  return EraseMember(pos, pos +1);
1577  }
1578 
1579  //! Remove members in the range [first, last) from an object.
1580  /*! \param first iterator to the first member to remove
1581  \param last iterator following the last member to remove
1582  \pre IsObject() == true && \ref MemberBegin() <= \c first <= \c last <= \ref MemberEnd()
1583  \return Iterator following the last removed element.
1584  \note This function preserves the relative order of the remaining object
1585  members.
1586  \note Linear time complexity.
1587  */
1588  MemberIterator EraseMember(ConstMemberIterator first, ConstMemberIterator last) {
1589  RAPIDJSON_ASSERT(IsObject());
1590  RAPIDJSON_ASSERT(data_.o.size > 0);
1591  RAPIDJSON_ASSERT(GetMembersPointer() != 0);
1592  RAPIDJSON_ASSERT(first >= MemberBegin());
1593  RAPIDJSON_ASSERT(first <= last);
1594  RAPIDJSON_ASSERT(last <= MemberEnd());
1595 
1596  MemberIterator pos = MemberBegin() + (first - MemberBegin());
1597  for (MemberIterator itr = pos; itr != last; ++itr)
1598  itr->~Member();
1599  std::memmove(static_cast<void*>(&*pos), &*last, static_cast<size_t>(MemberEnd() - last) * sizeof(Member));
1600  data_.o.size -= static_cast<SizeType>(last - first);
1601  return pos;
1602  }
1603 
1604  //! Erase a member in object by its name.
1605  /*! \param name Name of member to be removed.
1606  \return Whether the member existed.
1607  \note Linear time complexity.
1608  */
1609  bool EraseMember(const Ch* name) {
1610  GenericValue n(StringRef(name));
1611  return EraseMember(n);
1612  }
1613 
1614 #if RAPIDJSON_HAS_STDSTRING
1615  bool EraseMember(const std::basic_string<Ch>& name) { return EraseMember(GenericValue(StringRef(name))); }
1616 #endif
1617 
1618  template <typename SourceAllocator>
1619  bool EraseMember(const GenericValue<Encoding, SourceAllocator>& name) {
1620  MemberIterator m = FindMember(name);
1621  if (m != MemberEnd()) {
1622  EraseMember(m);
1623  return true;
1624  }
1625  else
1626  return false;
1627  }
1628 
1629  Object GetObject() { RAPIDJSON_ASSERT(IsObject()); return Object(*this); }
1630  ConstObject GetObject() const { RAPIDJSON_ASSERT(IsObject()); return ConstObject(*this); }
1631 
1632  //@}
1633 
1634  //!@name Array
1635  //@{
1636 
1637  //! Set this value as an empty array.
1638  /*! \post IsArray == true */
1639  GenericValue& SetArray() { this->~GenericValue(); new (this) GenericValue(kArrayType); return *this; }
1640 
1641  //! Get the number of elements in array.
1642  SizeType Size() const { RAPIDJSON_ASSERT(IsArray()); return data_.a.size; }
1643 
1644  //! Get the capacity of array.
1645  SizeType Capacity() const { RAPIDJSON_ASSERT(IsArray()); return data_.a.capacity; }
1646 
1647  //! Check whether the array is empty.
1648  bool Empty() const { RAPIDJSON_ASSERT(IsArray()); return data_.a.size == 0; }
1649 
1650  //! Remove all elements in the array.
1651  /*! This function do not deallocate memory in the array, i.e. the capacity is unchanged.
1652  \note Linear time complexity.
1653  */
1654  void Clear() {
1655  RAPIDJSON_ASSERT(IsArray());
1656  GenericValue* e = GetElementsPointer();
1657  for (GenericValue* v = e; v != e + data_.a.size; ++v)
1658  v->~GenericValue();
1659  data_.a.size = 0;
1660  }
1661 
1662  //! Get an element from array by index.
1663  /*! \pre IsArray() == true
1664  \param index Zero-based index of element.
1665  \see operator[](T*)
1666  */
1667  GenericValue& operator[](SizeType index) {
1668  RAPIDJSON_ASSERT(IsArray());
1669  RAPIDJSON_ASSERT(index < data_.a.size);
1670  return GetElementsPointer()[index];
1671  }
1672  const GenericValue& operator[](SizeType index) const { return const_cast<GenericValue&>(*this)[index]; }
1673 
1674  //! Element iterator
1675  /*! \pre IsArray() == true */
1676  ValueIterator Begin() { RAPIDJSON_ASSERT(IsArray()); return GetElementsPointer(); }
1677  //! \em Past-the-end element iterator
1678  /*! \pre IsArray() == true */
1679  ValueIterator End() { RAPIDJSON_ASSERT(IsArray()); return GetElementsPointer() + data_.a.size; }
1680  //! Constant element iterator
1681  /*! \pre IsArray() == true */
1682  ConstValueIterator Begin() const { return const_cast<GenericValue&>(*this).Begin(); }
1683  //! Constant \em past-the-end element iterator
1684  /*! \pre IsArray() == true */
1685  ConstValueIterator End() const { return const_cast<GenericValue&>(*this).End(); }
1686 
1687  //! Request the array to have enough capacity to store elements.
1688  /*! \param newCapacity The capacity that the array at least need to have.
1689  \param allocator Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
1690  \return The value itself for fluent API.
1691  \note Linear time complexity.
1692  */
1693  GenericValue& Reserve(SizeType newCapacity, Allocator &allocator) {
1694  RAPIDJSON_ASSERT(IsArray());
1695  if (newCapacity > data_.a.capacity) {
1696  SetElementsPointer(reinterpret_cast<GenericValue*>(allocator.Realloc(GetElementsPointer(), data_.a.capacity * sizeof(GenericValue), newCapacity * sizeof(GenericValue))));
1697  data_.a.capacity = newCapacity;
1698  }
1699  return *this;
1700  }
1701 
1702  //! Append a GenericValue at the end of the array.
1703  /*! \param value Value to be appended.
1704  \param allocator Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
1705  \pre IsArray() == true
1706  \post value.IsNull() == true
1707  \return The value itself for fluent API.
1708  \note The ownership of \c value will be transferred to this array on success.
1709  \note If the number of elements to be appended is known, calls Reserve() once first may be more efficient.
1710  \note Amortized constant time complexity.
1711  */
1712  GenericValue& PushBack(GenericValue& value, Allocator& allocator) {
1713  RAPIDJSON_ASSERT(IsArray());
1714  if (data_.a.size >= data_.a.capacity)
1715  Reserve(data_.a.capacity == 0 ? kDefaultArrayCapacity : (data_.a.capacity + (data_.a.capacity + 1) / 2), allocator);
1716  GetElementsPointer()[data_.a.size++].RawAssign(value);
1717  return *this;
1718  }
1719 
1720 #if RAPIDJSON_HAS_CXX11_RVALUE_REFS
1721  GenericValue& PushBack(GenericValue&& value, Allocator& allocator) {
1722  return PushBack(value, allocator);
1723  }
1724 #endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS
1725 
1726  //! Append a constant string reference at the end of the array.
1727  /*! \param value Constant string reference to be appended.
1728  \param allocator Allocator for reallocating memory. It must be the same one used previously. Commonly use GenericDocument::GetAllocator().
1729  \pre IsArray() == true
1730  \return The value itself for fluent API.
1731  \note If the number of elements to be appended is known, calls Reserve() once first may be more efficient.
1732  \note Amortized constant time complexity.
1733  \see GenericStringRef
1734  */
1735  GenericValue& PushBack(StringRefType value, Allocator& allocator) {
1736  return (*this).template PushBack<StringRefType>(value, allocator);
1737  }
1738 
1739  //! Append a primitive value at the end of the array.
1740  /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t
1741  \param value Value of primitive type T to be appended.
1742  \param allocator Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
1743  \pre IsArray() == true
1744  \return The value itself for fluent API.
1745  \note If the number of elements to be appended is known, calls Reserve() once first may be more efficient.
1746 
1747  \note The source type \c T explicitly disallows all pointer types,
1748  especially (\c const) \ref Ch*. This helps avoiding implicitly
1749  referencing character strings with insufficient lifetime, use
1750  \ref PushBack(GenericValue&, Allocator&) or \ref
1751  PushBack(StringRefType, Allocator&).
1752  All other pointer types would implicitly convert to \c bool,
1753  use an explicit cast instead, if needed.
1754  \note Amortized constant time complexity.
1755  */
1756  template <typename T>
1757  RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (GenericValue&))
1758  PushBack(T value, Allocator& allocator) {
1759  GenericValue v(value);
1760  return PushBack(v, allocator);
1761  }
1762 
1763  //! Remove the last element in the array.
1764  /*!
1765  \note Constant time complexity.
1766  */
1767  GenericValue& PopBack() {
1768  RAPIDJSON_ASSERT(IsArray());
1769  RAPIDJSON_ASSERT(!Empty());
1770  GetElementsPointer()[--data_.a.size].~GenericValue();
1771  return *this;
1772  }
1773 
1774  //! Remove an element of array by iterator.
1775  /*!
1776  \param pos iterator to the element to remove
1777  \pre IsArray() == true && \ref Begin() <= \c pos < \ref End()
1778  \return Iterator following the removed element. If the iterator pos refers to the last element, the End() iterator is returned.
1779  \note Linear time complexity.
1780  */
1781  ValueIterator Erase(ConstValueIterator pos) {
1782  return Erase(pos, pos + 1);
1783  }
1784 
1785  //! Remove elements in the range [first, last) of the array.
1786  /*!
1787  \param first iterator to the first element to remove
1788  \param last iterator following the last element to remove
1789  \pre IsArray() == true && \ref Begin() <= \c first <= \c last <= \ref End()
1790  \return Iterator following the last removed element.
1791  \note Linear time complexity.
1792  */
1793  ValueIterator Erase(ConstValueIterator first, ConstValueIterator last) {
1794  RAPIDJSON_ASSERT(IsArray());
1795  RAPIDJSON_ASSERT(data_.a.size > 0);
1796  RAPIDJSON_ASSERT(GetElementsPointer() != 0);
1797  RAPIDJSON_ASSERT(first >= Begin());
1798  RAPIDJSON_ASSERT(first <= last);
1799  RAPIDJSON_ASSERT(last <= End());
1800  ValueIterator pos = Begin() + (first - Begin());
1801  for (ValueIterator itr = pos; itr != last; ++itr)
1802  itr->~GenericValue();
1803  std::memmove(static_cast<void*>(pos), last, static_cast<size_t>(End() - last) * sizeof(GenericValue));
1804  data_.a.size -= static_cast<SizeType>(last - first);
1805  return pos;
1806  }
1807 
1808  Array GetArray() { RAPIDJSON_ASSERT(IsArray()); return Array(*this); }
1809  ConstArray GetArray() const { RAPIDJSON_ASSERT(IsArray()); return ConstArray(*this); }
1810 
1811  //@}
1812 
1813  //!@name Number
1814  //@{
1815 
1816  int GetInt() const { RAPIDJSON_ASSERT(data_.f.flags & kIntFlag); return data_.n.i.i; }
1817  unsigned GetUint() const { RAPIDJSON_ASSERT(data_.f.flags & kUintFlag); return data_.n.u.u; }
1818  int64_t GetInt64() const { RAPIDJSON_ASSERT(data_.f.flags & kInt64Flag); return data_.n.i64; }
1819  uint64_t GetUint64() const { RAPIDJSON_ASSERT(data_.f.flags & kUint64Flag); return data_.n.u64; }
1820 
1821  //! Get the value as double type.
1822  /*! \note If the value is 64-bit integer type, it may lose precision. Use \c IsLosslessDouble() to check whether the converison is lossless.
1823  */
1824  double GetDouble() const {
1825  RAPIDJSON_ASSERT(IsNumber());
1826  if ((data_.f.flags & kDoubleFlag) != 0) return data_.n.d; // exact type, no conversion.
1827  if ((data_.f.flags & kIntFlag) != 0) return data_.n.i.i; // int -> double
1828  if ((data_.f.flags & kUintFlag) != 0) return data_.n.u.u; // unsigned -> double
1829  if ((data_.f.flags & kInt64Flag) != 0) return static_cast<double>(data_.n.i64); // int64_t -> double (may lose precision)
1830  RAPIDJSON_ASSERT((data_.f.flags & kUint64Flag) != 0); return static_cast<double>(data_.n.u64); // uint64_t -> double (may lose precision)
1831  }
1832 
1833  //! Get the value as float type.
1834  /*! \note If the value is 64-bit integer type, it may lose precision. Use \c IsLosslessFloat() to check whether the converison is lossless.
1835  */
1836  float GetFloat() const {
1837  return static_cast<float>(GetDouble());
1838  }
1839 
1840  GenericValue& SetInt(int i) { this->~GenericValue(); new (this) GenericValue(i); return *this; }
1841  GenericValue& SetUint(unsigned u) { this->~GenericValue(); new (this) GenericValue(u); return *this; }
1842  GenericValue& SetInt64(int64_t i64) { this->~GenericValue(); new (this) GenericValue(i64); return *this; }
1843  GenericValue& SetUint64(uint64_t u64) { this->~GenericValue(); new (this) GenericValue(u64); return *this; }
1844  GenericValue& SetDouble(double d) { this->~GenericValue(); new (this) GenericValue(d); return *this; }
1845  GenericValue& SetFloat(float f) { this->~GenericValue(); new (this) GenericValue(static_cast<double>(f)); return *this; }
1846 
1847  //@}
1848 
1849  //!@name String
1850  //@{
1851 
1852  const Ch* GetString() const { RAPIDJSON_ASSERT(IsString()); return (data_.f.flags & kInlineStrFlag) ? data_.ss.str : GetStringPointer(); }
1853 
1854  //! Get the length of string.
1855  /*! Since rapidjson permits "\\u0000" in the json string, strlen(v.GetString()) may not equal to v.GetStringLength().
1856  */
1857  SizeType GetStringLength() const { RAPIDJSON_ASSERT(IsString()); return ((data_.f.flags & kInlineStrFlag) ? (data_.ss.GetLength()) : data_.s.length); }
1858 
1859  //! Set this value as a string without copying source string.
1860  /*! This version has better performance with supplied length, and also support string containing null character.
1861  \param s source string pointer.
1862  \param length The length of source string, excluding the trailing null terminator.
1863  \return The value itself for fluent API.
1864  \post IsString() == true && GetString() == s && GetStringLength() == length
1865  \see SetString(StringRefType)
1866  */
1867  GenericValue& SetString(const Ch* s, SizeType length) { return SetString(StringRef(s, length)); }
1868 
1869  //! Set this value as a string without copying source string.
1870  /*! \param s source string reference
1871  \return The value itself for fluent API.
1872  \post IsString() == true && GetString() == s && GetStringLength() == s.length
1873  */
1874  GenericValue& SetString(StringRefType s) { this->~GenericValue(); SetStringRaw(s); return *this; }
1875 
1876  //! Set this value as a string by copying from source string.
1877  /*! This version has better performance with supplied length, and also support string containing null character.
1878  \param s source string.
1879  \param length The length of source string, excluding the trailing null terminator.
1880  \param allocator Allocator for allocating copied buffer. Commonly use GenericDocument::GetAllocator().
1881  \return The value itself for fluent API.
1882  \post IsString() == true && GetString() != s && strcmp(GetString(),s) == 0 && GetStringLength() == length
1883  */
1884  GenericValue& SetString(const Ch* s, SizeType length, Allocator& allocator) { return SetString(StringRef(s, length), allocator); }
1885 
1886  //! Set this value as a string by copying from source string.
1887  /*! \param s source string.
1888  \param allocator Allocator for allocating copied buffer. Commonly use GenericDocument::GetAllocator().
1889  \return The value itself for fluent API.
1890  \post IsString() == true && GetString() != s && strcmp(GetString(),s) == 0 && GetStringLength() == length
1891  */
1892  GenericValue& SetString(const Ch* s, Allocator& allocator) { return SetString(StringRef(s), allocator); }
1893 
1894  //! Set this value as a string by copying from source string.
1895  /*! \param s source string reference
1896  \param allocator Allocator for allocating copied buffer. Commonly use GenericDocument::GetAllocator().
1897  \return The value itself for fluent API.
1898  \post IsString() == true && GetString() != s.s && strcmp(GetString(),s) == 0 && GetStringLength() == length
1899  */
1900  GenericValue& SetString(StringRefType s, Allocator& allocator) { this->~GenericValue(); SetStringRaw(s, allocator); return *this; }
1901 
1902 #if RAPIDJSON_HAS_STDSTRING
1903  //! Set this value as a string by copying from source string.
1904  /*! \param s source string.
1905  \param allocator Allocator for allocating copied buffer. Commonly use GenericDocument::GetAllocator().
1906  \return The value itself for fluent API.
1907  \post IsString() == true && GetString() != s.data() && strcmp(GetString(),s.data() == 0 && GetStringLength() == s.size()
1908  \note Requires the definition of the preprocessor symbol \ref RAPIDJSON_HAS_STDSTRING.
1909  */
1910  GenericValue& SetString(const std::basic_string<Ch>& s, Allocator& allocator) { return SetString(StringRef(s), allocator); }
1911 #endif
1912 
1913  //@}
1914 
1915  //!@name Array
1916  //@{
1917 
1918  //! Templated version for checking whether this value is type T.
1919  /*!
1920  \tparam T Either \c bool, \c int, \c unsigned, \c int64_t, \c uint64_t, \c double, \c float, \c const \c char*, \c std::basic_string<Ch>
1921  */
1922  template <typename T>
1923  bool Is() const { return internal::TypeHelper<ValueType, T>::Is(*this); }
1924 
1925  template <typename T>
1926  T Get() const { return internal::TypeHelper<ValueType, T>::Get(*this); }
1927 
1928  template <typename T>
1929  T Get() { return internal::TypeHelper<ValueType, T>::Get(*this); }
1930 
1931  template<typename T>
1932  ValueType& Set(const T& data) { return internal::TypeHelper<ValueType, T>::Set(*this, data); }
1933 
1934  template<typename T>
1935  ValueType& Set(const T& data, AllocatorType& allocator) { return internal::TypeHelper<ValueType, T>::Set(*this, data, allocator); }
1936 
1937  //@}
1938 
1939  //! Generate events of this value to a Handler.
1940  /*! This function adopts the GoF visitor pattern.
1941  Typical usage is to output this JSON value as JSON text via Writer, which is a Handler.
1942  It can also be used to deep clone this value via GenericDocument, which is also a Handler.
1943  \tparam Handler type of handler.
1944  \param handler An object implementing concept Handler.
1945  */
1946  template <typename Handler>
1947  bool Accept(Handler& handler) const {
1948  switch(GetType()) {
1949  case kNullType: return handler.Null();
1950  case kFalseType: return handler.Bool(false);
1951  case kTrueType: return handler.Bool(true);
1952 
1953  case kObjectType:
1954  if (RAPIDJSON_UNLIKELY(!handler.StartObject()))
1955  return false;
1956  for (ConstMemberIterator m = MemberBegin(); m != MemberEnd(); ++m) {
1957  RAPIDJSON_ASSERT(m->name.IsString()); // User may change the type of name by MemberIterator.
1958  if (RAPIDJSON_UNLIKELY(!handler.Key(m->name.GetString(), m->name.GetStringLength(), (m->name.data_.f.flags & kCopyFlag) != 0)))
1959  return false;
1960  if (RAPIDJSON_UNLIKELY(!m->value.Accept(handler)))
1961  return false;
1962  }
1963  return handler.EndObject(data_.o.size);
1964 
1965  case kArrayType:
1966  if (RAPIDJSON_UNLIKELY(!handler.StartArray()))
1967  return false;
1968  for (const GenericValue* v = Begin(); v != End(); ++v)
1969  if (RAPIDJSON_UNLIKELY(!v->Accept(handler)))
1970  return false;
1971  return handler.EndArray(data_.a.size);
1972 
1973  case kStringType:
1974  return handler.String(GetString(), GetStringLength(), (data_.f.flags & kCopyFlag) != 0);
1975 
1976  default:
1977  RAPIDJSON_ASSERT(GetType() == kNumberType);
1978  if (IsDouble()) return handler.Double(data_.n.d);
1979  else if (IsInt()) return handler.Int(data_.n.i.i);
1980  else if (IsUint()) return handler.Uint(data_.n.u.u);
1981  else if (IsInt64()) return handler.Int64(data_.n.i64);
1982  else return handler.Uint64(data_.n.u64);
1983  }
1984  }
1985 
1986 private:
1987  template <typename, typename> friend class GenericValue;
1988  template <typename, typename, typename> friend class GenericDocument;
1989 
1990  enum {
1991  kBoolFlag = 0x0008,
1992  kNumberFlag = 0x0010,
1993  kIntFlag = 0x0020,
1994  kUintFlag = 0x0040,
1995  kInt64Flag = 0x0080,
1996  kUint64Flag = 0x0100,
1997  kDoubleFlag = 0x0200,
1998  kStringFlag = 0x0400,
1999  kCopyFlag = 0x0800,
2000  kInlineStrFlag = 0x1000,
2001 
2002  // Initial flags of different types.
2003  kNullFlag = kNullType,
2004  kTrueFlag = kTrueType | kBoolFlag,
2005  kFalseFlag = kFalseType | kBoolFlag,
2006  kNumberIntFlag = kNumberType | kNumberFlag | kIntFlag | kInt64Flag,
2007  kNumberUintFlag = kNumberType | kNumberFlag | kUintFlag | kUint64Flag | kInt64Flag,
2008  kNumberInt64Flag = kNumberType | kNumberFlag | kInt64Flag,
2009  kNumberUint64Flag = kNumberType | kNumberFlag | kUint64Flag,
2010  kNumberDoubleFlag = kNumberType | kNumberFlag | kDoubleFlag,
2011  kNumberAnyFlag = kNumberType | kNumberFlag | kIntFlag | kInt64Flag | kUintFlag | kUint64Flag | kDoubleFlag,
2012  kConstStringFlag = kStringType | kStringFlag,
2013  kCopyStringFlag = kStringType | kStringFlag | kCopyFlag,
2014  kShortStringFlag = kStringType | kStringFlag | kCopyFlag | kInlineStrFlag,
2015  kObjectFlag = kObjectType,
2016  kArrayFlag = kArrayType,
2017 
2018  kTypeMask = 0x07
2019  };
2020 
2021  static const SizeType kDefaultArrayCapacity = RAPIDJSON_VALUE_DEFAULT_ARRAY_CAPACITY;
2022  static const SizeType kDefaultObjectCapacity = RAPIDJSON_VALUE_DEFAULT_OBJECT_CAPACITY;
2023 
2024  struct Flag {
2025 #if RAPIDJSON_48BITPOINTER_OPTIMIZATION
2026  char payload[sizeof(SizeType) * 2 + 6]; // 2 x SizeType + lower 48-bit pointer
2027 #elif RAPIDJSON_64BIT
2028  char payload[sizeof(SizeType) * 2 + sizeof(void*) + 6]; // 6 padding bytes
2029 #else
2030  char payload[sizeof(SizeType) * 2 + sizeof(void*) + 2]; // 2 padding bytes
2031 #endif
2032  uint16_t flags;
2033  };
2034 
2035  struct String {
2036  SizeType length;
2037  SizeType hashcode; //!< reserved
2038  const Ch* str;
2039  }; // 12 bytes in 32-bit mode, 16 bytes in 64-bit mode
2040 
2041  // implementation detail: ShortString can represent zero-terminated strings up to MaxSize chars
2042  // (excluding the terminating zero) and store a value to determine the length of the contained
2043  // string in the last character str[LenPos] by storing "MaxSize - length" there. If the string
2044  // to store has the maximal length of MaxSize then str[LenPos] will be 0 and therefore act as
2045  // the string terminator as well. For getting the string length back from that value just use
2046  // "MaxSize - str[LenPos]".
2047  // This allows to store 13-chars strings in 32-bit mode, 21-chars strings in 64-bit mode,
2048  // 13-chars strings for RAPIDJSON_48BITPOINTER_OPTIMIZATION=1 inline (for `UTF8`-encoded strings).
2049  struct ShortString {
2050  enum { MaxChars = sizeof(static_cast<Flag*>(0)->payload) / sizeof(Ch), MaxSize = MaxChars - 1, LenPos = MaxSize };
2051  Ch str[MaxChars];
2052 
2053  inline static bool Usable(SizeType len) { return (MaxSize >= len); }
2054  inline void SetLength(SizeType len) { str[LenPos] = static_cast<Ch>(MaxSize - len); }
2055  inline SizeType GetLength() const { return static_cast<SizeType>(MaxSize - str[LenPos]); }
2056  }; // at most as many bytes as "String" above => 12 bytes in 32-bit mode, 16 bytes in 64-bit mode
2057 
2058  // By using proper binary layout, retrieval of different integer types do not need conversions.
2059  union Number {
2060 #if RAPIDJSON_ENDIAN == RAPIDJSON_LITTLEENDIAN
2061  struct I {
2062  int i;
2063  char padding[4];
2064  }i;
2065  struct U {
2066  unsigned u;
2067  char padding2[4];
2068  }u;
2069 #else
2070  struct I {
2071  char padding[4];
2072  int i;
2073  }i;
2074  struct U {
2075  char padding2[4];
2076  unsigned u;
2077  }u;
2078 #endif
2079  int64_t i64;
2080  uint64_t u64;
2081  double d;
2082  }; // 8 bytes
2083 
2084  struct ObjectData {
2085  SizeType size;
2086  SizeType capacity;
2087  Member* members;
2088  }; // 12 bytes in 32-bit mode, 16 bytes in 64-bit mode
2089 
2090  struct ArrayData {
2091  SizeType size;
2092  SizeType capacity;
2093  GenericValue* elements;
2094  }; // 12 bytes in 32-bit mode, 16 bytes in 64-bit mode
2095 
2096  union Data {
2097  String s;
2098  ShortString ss;
2099  Number n;
2100  ObjectData o;
2101  ArrayData a;
2102  Flag f;
2103  }; // 16 bytes in 32-bit mode, 24 bytes in 64-bit mode, 16 bytes in 64-bit with RAPIDJSON_48BITPOINTER_OPTIMIZATION
2104 
2105  RAPIDJSON_FORCEINLINE const Ch* GetStringPointer() const { return RAPIDJSON_GETPOINTER(Ch, data_.s.str); }
2106  RAPIDJSON_FORCEINLINE const Ch* SetStringPointer(const Ch* str) { return RAPIDJSON_SETPOINTER(Ch, data_.s.str, str); }
2107  RAPIDJSON_FORCEINLINE GenericValue* GetElementsPointer() const { return RAPIDJSON_GETPOINTER(GenericValue, data_.a.elements); }
2108  RAPIDJSON_FORCEINLINE GenericValue* SetElementsPointer(GenericValue* elements) { return RAPIDJSON_SETPOINTER(GenericValue, data_.a.elements, elements); }
2109  RAPIDJSON_FORCEINLINE Member* GetMembersPointer() const { return RAPIDJSON_GETPOINTER(Member, data_.o.members); }
2110  RAPIDJSON_FORCEINLINE Member* SetMembersPointer(Member* members) { return RAPIDJSON_SETPOINTER(Member, data_.o.members, members); }
2111 
2112  // Initialize this value as array with initial data, without calling destructor.
2113  void SetArrayRaw(GenericValue* values, SizeType count, Allocator& allocator) {
2114  data_.f.flags = kArrayFlag;
2115  if (count) {
2116  GenericValue* e = static_cast<GenericValue*>(allocator.Malloc(count * sizeof(GenericValue)));
2117  SetElementsPointer(e);
2118  std::memcpy(static_cast<void*>(e), values, count * sizeof(GenericValue));
2119  }
2120  else
2121  SetElementsPointer(0);
2122  data_.a.size = data_.a.capacity = count;
2123  }
2124 
2125  //! Initialize this value as object with initial data, without calling destructor.
2126  void SetObjectRaw(Member* members, SizeType count, Allocator& allocator) {
2127  data_.f.flags = kObjectFlag;
2128  if (count) {
2129  Member* m = static_cast<Member*>(allocator.Malloc(count * sizeof(Member)));
2130  SetMembersPointer(m);
2131  std::memcpy(static_cast<void*>(m), members, count * sizeof(Member));
2132  }
2133  else
2134  SetMembersPointer(0);
2135  data_.o.size = data_.o.capacity = count;
2136  }
2137 
2138  //! Initialize this value as constant string, without calling destructor.
2139  void SetStringRaw(StringRefType s) RAPIDJSON_NOEXCEPT {
2140  data_.f.flags = kConstStringFlag;
2141  SetStringPointer(s);
2142  data_.s.length = s.length;
2143  }
2144 
2145  //! Initialize this value as copy string with initial data, without calling destructor.
2146  void SetStringRaw(StringRefType s, Allocator& allocator) {
2147  Ch* str = 0;
2148  if (ShortString::Usable(s.length)) {
2149  data_.f.flags = kShortStringFlag;
2150  data_.ss.SetLength(s.length);
2151  str = data_.ss.str;
2152  } else {
2153  data_.f.flags = kCopyStringFlag;
2154  data_.s.length = s.length;
2155  str = static_cast<Ch *>(allocator.Malloc((s.length + 1) * sizeof(Ch)));
2156  SetStringPointer(str);
2157  }
2158  std::memcpy(str, s, s.length * sizeof(Ch));
2159  str[s.length] = '\0';
2160  }
2161 
2162  //! Assignment without calling destructor
2163  void RawAssign(GenericValue& rhs) RAPIDJSON_NOEXCEPT {
2164  data_ = rhs.data_;
2165  // data_.f.flags = rhs.data_.f.flags;
2166  rhs.data_.f.flags = kNullFlag;
2167  }
2168 
2169  template <typename SourceAllocator>
2170  bool StringEqual(const GenericValue<Encoding, SourceAllocator>& rhs) const {
2171  RAPIDJSON_ASSERT(IsString());
2172  RAPIDJSON_ASSERT(rhs.IsString());
2173 
2174  const SizeType len1 = GetStringLength();
2175  const SizeType len2 = rhs.GetStringLength();
2176  if(len1 != len2) { return false; }
2177 
2178  const Ch* const str1 = GetString();
2179  const Ch* const str2 = rhs.GetString();
2180  if(str1 == str2) { return true; } // fast path for constant string
2181 
2182  return (std::memcmp(str1, str2, sizeof(Ch) * len1) == 0);
2183  }
2184 
2185  Data data_;
2186 };
2187 
2188 //! GenericValue with UTF8 encoding
2190 
2191 ///////////////////////////////////////////////////////////////////////////////
2192 // GenericDocument
2193 
2194 //! A document for parsing JSON text as DOM.
2195 /*!
2196  \note implements Handler concept
2197  \tparam Encoding Encoding for both parsing and string storage.
2198  \tparam Allocator Allocator for allocating memory for the DOM
2199  \tparam StackAllocator Allocator for allocating memory for stack during parsing.
2200  \warning Although GenericDocument inherits from GenericValue, the API does \b not provide any virtual functions, especially no virtual destructor. To avoid memory leaks, do not \c delete a GenericDocument object via a pointer to a GenericValue.
2201 */
2202 template <typename Encoding, typename Allocator = RAPIDJSON_DEFAULT_ALLOCATOR, typename StackAllocator = RAPIDJSON_DEFAULT_STACK_ALLOCATOR >
2203 class GenericDocument : public GenericValue<Encoding, Allocator> {
2204 public:
2205  typedef typename Encoding::Ch Ch; //!< Character type derived from Encoding.
2206  typedef GenericValue<Encoding, Allocator> ValueType; //!< Value type of the document.
2207  typedef Allocator AllocatorType; //!< Allocator type from template parameter.
2208 
2209  //! Constructor
2210  /*! Creates an empty document of specified type.
2211  \param type Mandatory type of object to create.
2212  \param allocator Optional allocator for allocating memory.
2213  \param stackCapacity Optional initial capacity of stack in bytes.
2214  \param stackAllocator Optional allocator for allocating memory for stack.
2215  */
2216  explicit GenericDocument(Type type, Allocator* allocator = 0, size_t stackCapacity = kDefaultStackCapacity, StackAllocator* stackAllocator = 0) :
2217  GenericValue<Encoding, Allocator>(type), allocator_(allocator), ownAllocator_(0), stack_(stackAllocator, stackCapacity), parseResult_()
2218  {
2219  if (!allocator_)
2220  ownAllocator_ = allocator_ = RAPIDJSON_NEW(Allocator)();
2221  }
2222 
2223  //! Constructor
2224  /*! Creates an empty document which type is Null.
2225  \param allocator Optional allocator for allocating memory.
2226  \param stackCapacity Optional initial capacity of stack in bytes.
2227  \param stackAllocator Optional allocator for allocating memory for stack.
2228  */
2229  GenericDocument(Allocator* allocator = 0, size_t stackCapacity = kDefaultStackCapacity, StackAllocator* stackAllocator = 0) :
2230  allocator_(allocator), ownAllocator_(0), stack_(stackAllocator, stackCapacity), parseResult_()
2231  {
2232  if (!allocator_)
2233  ownAllocator_ = allocator_ = RAPIDJSON_NEW(Allocator)();
2234  }
2235 
2236 #if RAPIDJSON_HAS_CXX11_RVALUE_REFS
2237  //! Move constructor in C++11
2238  GenericDocument(GenericDocument&& rhs) RAPIDJSON_NOEXCEPT
2239  : ValueType(std::forward<ValueType>(rhs)), // explicit cast to avoid prohibited move from Document
2240  allocator_(rhs.allocator_),
2241  ownAllocator_(rhs.ownAllocator_),
2242  stack_(std::move(rhs.stack_)),
2243  parseResult_(rhs.parseResult_)
2244  {
2245  rhs.allocator_ = 0;
2246  rhs.ownAllocator_ = 0;
2247  rhs.parseResult_ = ParseResult();
2248  }
2249 #endif
2250 
2251  ~GenericDocument() {
2252  Destroy();
2253  }
2254 
2255 #if RAPIDJSON_HAS_CXX11_RVALUE_REFS
2256  //! Move assignment in C++11
2257  GenericDocument& operator=(GenericDocument&& rhs) RAPIDJSON_NOEXCEPT
2258  {
2259  // The cast to ValueType is necessary here, because otherwise it would
2260  // attempt to call GenericValue's templated assignment operator.
2261  ValueType::operator=(std::forward<ValueType>(rhs));
2262 
2263  // Calling the destructor here would prematurely call stack_'s destructor
2264  Destroy();
2265 
2266  allocator_ = rhs.allocator_;
2267  ownAllocator_ = rhs.ownAllocator_;
2268  stack_ = std::move(rhs.stack_);
2269  parseResult_ = rhs.parseResult_;
2270 
2271  rhs.allocator_ = 0;
2272  rhs.ownAllocator_ = 0;
2273  rhs.parseResult_ = ParseResult();
2274 
2275  return *this;
2276  }
2277 #endif
2278 
2279  //! Exchange the contents of this document with those of another.
2280  /*!
2281  \param rhs Another document.
2282  \note Constant complexity.
2283  \see GenericValue::Swap
2284  */
2285  GenericDocument& Swap(GenericDocument& rhs) RAPIDJSON_NOEXCEPT {
2286  ValueType::Swap(rhs);
2287  stack_.Swap(rhs.stack_);
2288  internal::Swap(allocator_, rhs.allocator_);
2289  internal::Swap(ownAllocator_, rhs.ownAllocator_);
2290  internal::Swap(parseResult_, rhs.parseResult_);
2291  return *this;
2292  }
2293 
2294  // Allow Swap with ValueType.
2295  // Refer to Effective C++ 3rd Edition/Item 33: Avoid hiding inherited names.
2296  using ValueType::Swap;
2297 
2298  //! free-standing swap function helper
2299  /*!
2300  Helper function to enable support for common swap implementation pattern based on \c std::swap:
2301  \code
2302  void swap(MyClass& a, MyClass& b) {
2303  using std::swap;
2304  swap(a.doc, b.doc);
2305  // ...
2306  }
2307  \endcode
2308  \see Swap()
2309  */
2310  friend inline void swap(GenericDocument& a, GenericDocument& b) RAPIDJSON_NOEXCEPT { a.Swap(b); }
2311 
2312  //! Populate this document by a generator which produces SAX events.
2313  /*! \tparam Generator A functor with <tt>bool f(Handler)</tt> prototype.
2314  \param g Generator functor which sends SAX events to the parameter.
2315  \return The document itself for fluent API.
2316  */
2317  template <typename Generator>
2318  GenericDocument& Populate(Generator& g) {
2319  ClearStackOnExit scope(*this);
2320  if (g(*this)) {
2321  RAPIDJSON_ASSERT(stack_.GetSize() == sizeof(ValueType)); // Got one and only one root object
2322  ValueType::operator=(*stack_.template Pop<ValueType>(1));// Move value from stack to document
2323  }
2324  return *this;
2325  }
2326 
2327  //!@name Parse from stream
2328  //!@{
2329 
2330  //! Parse JSON text from an input stream (with Encoding conversion)
2331  /*! \tparam parseFlags Combination of \ref ParseFlag.
2332  \tparam SourceEncoding Encoding of input stream
2333  \tparam InputStream Type of input stream, implementing Stream concept
2334  \param is Input stream to be parsed.
2335  \return The document itself for fluent API.
2336  */
2337  template <unsigned parseFlags, typename SourceEncoding, typename InputStream>
2338  GenericDocument& ParseStream(InputStream& is) {
2340  stack_.HasAllocator() ? &stack_.GetAllocator() : 0);
2341  ClearStackOnExit scope(*this);
2342  parseResult_ = reader.template Parse<parseFlags>(is, *this);
2343  if (parseResult_) {
2344  RAPIDJSON_ASSERT(stack_.GetSize() == sizeof(ValueType)); // Got one and only one root object
2345  ValueType::operator=(*stack_.template Pop<ValueType>(1));// Move value from stack to document
2346  }
2347  return *this;
2348  }
2349 
2350  //! Parse JSON text from an input stream
2351  /*! \tparam parseFlags Combination of \ref ParseFlag.
2352  \tparam InputStream Type of input stream, implementing Stream concept
2353  \param is Input stream to be parsed.
2354  \return The document itself for fluent API.
2355  */
2356  template <unsigned parseFlags, typename InputStream>
2357  GenericDocument& ParseStream(InputStream& is) {
2358  return ParseStream<parseFlags, Encoding, InputStream>(is);
2359  }
2360 
2361  //! Parse JSON text from an input stream (with \ref kParseDefaultFlags)
2362  /*! \tparam InputStream Type of input stream, implementing Stream concept
2363  \param is Input stream to be parsed.
2364  \return The document itself for fluent API.
2365  */
2366  template <typename InputStream>
2367  GenericDocument& ParseStream(InputStream& is) {
2368  return ParseStream<kParseDefaultFlags, Encoding, InputStream>(is);
2369  }
2370  //!@}
2371 
2372  //!@name Parse in-place from mutable string
2373  //!@{
2374 
2375  //! Parse JSON text from a mutable string
2376  /*! \tparam parseFlags Combination of \ref ParseFlag.
2377  \param str Mutable zero-terminated string to be parsed.
2378  \return The document itself for fluent API.
2379  */
2380  template <unsigned parseFlags>
2383  return ParseStream<parseFlags | kParseInsituFlag>(s);
2384  }
2385 
2386  //! Parse JSON text from a mutable string (with \ref kParseDefaultFlags)
2387  /*! \param str Mutable zero-terminated string to be parsed.
2388  \return The document itself for fluent API.
2389  */
2391  return ParseInsitu<kParseDefaultFlags>(str);
2392  }
2393  //!@}
2394 
2395  //!@name Parse from read-only string
2396  //!@{
2397 
2398  //! Parse JSON text from a read-only string (with Encoding conversion)
2399  /*! \tparam parseFlags Combination of \ref ParseFlag (must not contain \ref kParseInsituFlag).
2400  \tparam SourceEncoding Transcoding from input Encoding
2401  \param str Read-only zero-terminated string to be parsed.
2402  */
2403  template <unsigned parseFlags, typename SourceEncoding>
2404  GenericDocument& Parse(const typename SourceEncoding::Ch* str) {
2405  RAPIDJSON_ASSERT(!(parseFlags & kParseInsituFlag));
2407  return ParseStream<parseFlags, SourceEncoding>(s);
2408  }
2409 
2410  //! Parse JSON text from a read-only string
2411  /*! \tparam parseFlags Combination of \ref ParseFlag (must not contain \ref kParseInsituFlag).
2412  \param str Read-only zero-terminated string to be parsed.
2413  */
2414  template <unsigned parseFlags>
2415  GenericDocument& Parse(const Ch* str) {
2416  return Parse<parseFlags, Encoding>(str);
2417  }
2418 
2419  //! Parse JSON text from a read-only string (with \ref kParseDefaultFlags)
2420  /*! \param str Read-only zero-terminated string to be parsed.
2421  */
2422  GenericDocument& Parse(const Ch* str) {
2423  return Parse<kParseDefaultFlags>(str);
2424  }
2425 
2426  template <unsigned parseFlags, typename SourceEncoding>
2427  GenericDocument& Parse(const typename SourceEncoding::Ch* str, size_t length) {
2428  RAPIDJSON_ASSERT(!(parseFlags & kParseInsituFlag));
2429  MemoryStream ms(reinterpret_cast<const char*>(str), length * sizeof(typename SourceEncoding::Ch));
2431  ParseStream<parseFlags, SourceEncoding>(is);
2432  return *this;
2433  }
2434 
2435  template <unsigned parseFlags>
2436  GenericDocument& Parse(const Ch* str, size_t length) {
2437  return Parse<parseFlags, Encoding>(str, length);
2438  }
2439 
2440  GenericDocument& Parse(const Ch* str, size_t length) {
2441  return Parse<kParseDefaultFlags>(str, length);
2442  }
2443 
2444 #if RAPIDJSON_HAS_STDSTRING
2445  template <unsigned parseFlags, typename SourceEncoding>
2446  GenericDocument& Parse(const std::basic_string<typename SourceEncoding::Ch>& str) {
2447  // c_str() is constant complexity according to standard. Should be faster than Parse(const char*, size_t)
2448  return Parse<parseFlags, SourceEncoding>(str.c_str());
2449  }
2450 
2451  template <unsigned parseFlags>
2452  GenericDocument& Parse(const std::basic_string<Ch>& str) {
2453  return Parse<parseFlags, Encoding>(str.c_str());
2454  }
2455 
2456  GenericDocument& Parse(const std::basic_string<Ch>& str) {
2457  return Parse<kParseDefaultFlags>(str);
2458  }
2459 #endif // RAPIDJSON_HAS_STDSTRING
2460 
2461  //!@}
2462 
2463  //!@name Handling parse errors
2464  //!@{
2465 
2466  //! Whether a parse error has occurred in the last parsing.
2467  bool HasParseError() const { return parseResult_.IsError(); }
2468 
2469  //! Get the \ref ParseErrorCode of last parsing.
2470  ParseErrorCode GetParseError() const { return parseResult_.Code(); }
2471 
2472  //! Get the position of last parsing error in input, 0 otherwise.
2473  size_t GetErrorOffset() const { return parseResult_.Offset(); }
2474 
2475  //! Implicit conversion to get the last parse result
2476 #ifndef __clang // -Wdocumentation
2477  /*! \return \ref ParseResult of the last parse operation
2478 
2479  \code
2480  Document doc;
2481  ParseResult ok = doc.Parse(json);
2482  if (!ok)
2483  printf( "JSON parse error: %s (%u)\n", GetParseError_En(ok.Code()), ok.Offset());
2484  \endcode
2485  */
2486 #endif
2487  operator ParseResult() const { return parseResult_; }
2488  //!@}
2489 
2490  //! Get the allocator of this document.
2492  RAPIDJSON_ASSERT(allocator_);
2493  return *allocator_;
2494  }
2495 
2496  //! Get the capacity of stack in bytes.
2497  size_t GetStackCapacity() const { return stack_.GetCapacity(); }
2498 
2499 private:
2500  // clear stack on any exit from ParseStream, e.g. due to exception
2501  struct ClearStackOnExit {
2502  explicit ClearStackOnExit(GenericDocument& d) : d_(d) {}
2503  ~ClearStackOnExit() { d_.ClearStack(); }
2504  private:
2505  ClearStackOnExit(const ClearStackOnExit&);
2506  ClearStackOnExit& operator=(const ClearStackOnExit&);
2507  GenericDocument& d_;
2508  };
2509 
2510  // callers of the following private Handler functions
2511  // template <typename,typename,typename> friend class GenericReader; // for parsing
2512  template <typename, typename> friend class GenericValue; // for deep copying
2513 
2514 public:
2515  // Implementation of Handler
2516  bool Null() { new (stack_.template Push<ValueType>()) ValueType(); return true; }
2517  bool Bool(bool b) { new (stack_.template Push<ValueType>()) ValueType(b); return true; }
2518  bool Int(int i) { new (stack_.template Push<ValueType>()) ValueType(i); return true; }
2519  bool Uint(unsigned i) { new (stack_.template Push<ValueType>()) ValueType(i); return true; }
2520  bool Int64(int64_t i) { new (stack_.template Push<ValueType>()) ValueType(i); return true; }
2521  bool Uint64(uint64_t i) { new (stack_.template Push<ValueType>()) ValueType(i); return true; }
2522  bool Double(double d) { new (stack_.template Push<ValueType>()) ValueType(d); return true; }
2523 
2524  bool RawNumber(const Ch* str, SizeType length, bool copy) {
2525  if (copy)
2526  new (stack_.template Push<ValueType>()) ValueType(str, length, GetAllocator());
2527  else
2528  new (stack_.template Push<ValueType>()) ValueType(str, length);
2529  return true;
2530  }
2531 
2532  bool String(const Ch* str, SizeType length, bool copy) {
2533  if (copy)
2534  new (stack_.template Push<ValueType>()) ValueType(str, length, GetAllocator());
2535  else
2536  new (stack_.template Push<ValueType>()) ValueType(str, length);
2537  return true;
2538  }
2539 
2540  bool StartObject() { new (stack_.template Push<ValueType>()) ValueType(kObjectType); return true; }
2541 
2542  bool Key(const Ch* str, SizeType length, bool copy) { return String(str, length, copy); }
2543 
2544  bool EndObject(SizeType memberCount) {
2545  typename ValueType::Member* members = stack_.template Pop<typename ValueType::Member>(memberCount);
2546  stack_.template Top<ValueType>()->SetObjectRaw(members, memberCount, GetAllocator());
2547  return true;
2548  }
2549 
2550  bool StartArray() { new (stack_.template Push<ValueType>()) ValueType(kArrayType); return true; }
2551 
2552  bool EndArray(SizeType elementCount) {
2553  ValueType* elements = stack_.template Pop<ValueType>(elementCount);
2554  stack_.template Top<ValueType>()->SetArrayRaw(elements, elementCount, GetAllocator());
2555  return true;
2556  }
2557 
2558 private:
2559  //! Prohibit copying
2560  GenericDocument(const GenericDocument&);
2561  //! Prohibit assignment
2562  GenericDocument& operator=(const GenericDocument&);
2563 
2564  void ClearStack() {
2565  if (Allocator::kNeedFree)
2566  while (stack_.GetSize() > 0) // Here assumes all elements in stack array are GenericValue (Member is actually 2 GenericValue objects)
2567  (stack_.template Pop<ValueType>(1))->~ValueType();
2568  else
2569  stack_.Clear();
2570  stack_.ShrinkToFit();
2571  }
2572 
2573  void Destroy() {
2574  RAPIDJSON_DELETE(ownAllocator_);
2575  }
2576 
2577  static const size_t kDefaultStackCapacity = 1024;
2578  Allocator* allocator_;
2579  Allocator* ownAllocator_;
2580  internal::Stack<StackAllocator> stack_;
2581  ParseResult parseResult_;
2582 };
2583 
2584 //! GenericDocument with UTF8 encoding
2586 
2587 
2588 //! Helper class for accessing Value of array type.
2589 /*!
2590  Instance of this helper class is obtained by \c GenericValue::GetArray().
2591  In addition to all APIs for array type, it provides range-based for loop if \c RAPIDJSON_HAS_CXX11_RANGE_FOR=1.
2592 */
2593 template <bool Const, typename ValueT>
2594 class GenericArray {
2595 public:
2596  typedef GenericArray<true, ValueT> ConstArray;
2597  typedef GenericArray<false, ValueT> Array;
2598  typedef ValueT PlainType;
2599  typedef typename internal::MaybeAddConst<Const,PlainType>::Type ValueType;
2600  typedef ValueType* ValueIterator; // This may be const or non-const iterator
2601  typedef const ValueT* ConstValueIterator;
2602  typedef typename ValueType::AllocatorType AllocatorType;
2603  typedef typename ValueType::StringRefType StringRefType;
2604 
2605  template <typename, typename>
2606  friend class GenericValue;
2607 
2608  GenericArray(const GenericArray& rhs) : value_(rhs.value_) {}
2609  GenericArray& operator=(const GenericArray& rhs) { value_ = rhs.value_; return *this; }
2610  ~GenericArray() {}
2611 
2612  SizeType Size() const { return value_.Size(); }
2613  SizeType Capacity() const { return value_.Capacity(); }
2614  bool Empty() const { return value_.Empty(); }
2615  void Clear() const { value_.Clear(); }
2616  ValueType& operator[](SizeType index) const { return value_[index]; }
2617  ValueIterator Begin() const { return value_.Begin(); }
2618  ValueIterator End() const { return value_.End(); }
2619  GenericArray Reserve(SizeType newCapacity, AllocatorType &allocator) const { value_.Reserve(newCapacity, allocator); return *this; }
2620  GenericArray PushBack(ValueType& value, AllocatorType& allocator) const { value_.PushBack(value, allocator); return *this; }
2621 #if RAPIDJSON_HAS_CXX11_RVALUE_REFS
2622  GenericArray PushBack(ValueType&& value, AllocatorType& allocator) const { value_.PushBack(value, allocator); return *this; }
2623 #endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS
2624  GenericArray PushBack(StringRefType value, AllocatorType& allocator) const { value_.PushBack(value, allocator); return *this; }
2625  template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (const GenericArray&)) PushBack(T value, AllocatorType& allocator) const { value_.PushBack(value, allocator); return *this; }
2626  GenericArray PopBack() const { value_.PopBack(); return *this; }
2627  ValueIterator Erase(ConstValueIterator pos) const { return value_.Erase(pos); }
2628  ValueIterator Erase(ConstValueIterator first, ConstValueIterator last) const { return value_.Erase(first, last); }
2629 
2630 #if RAPIDJSON_HAS_CXX11_RANGE_FOR
2631  ValueIterator begin() const { return value_.Begin(); }
2632  ValueIterator end() const { return value_.End(); }
2633 #endif
2634 
2635 private:
2636  GenericArray();
2637  GenericArray(ValueType& value) : value_(value) {}
2638  ValueType& value_;
2639 };
2640 
2641 //! Helper class for accessing Value of object type.
2642 /*!
2643  Instance of this helper class is obtained by \c GenericValue::GetObject().
2644  In addition to all APIs for array type, it provides range-based for loop if \c RAPIDJSON_HAS_CXX11_RANGE_FOR=1.
2645 */
2646 template <bool Const, typename ValueT>
2647 class GenericObject {
2648 public:
2649  typedef GenericObject<true, ValueT> ConstObject;
2650  typedef GenericObject<false, ValueT> Object;
2651  typedef ValueT PlainType;
2652  typedef typename internal::MaybeAddConst<Const,PlainType>::Type ValueType;
2653  typedef GenericMemberIterator<Const, typename ValueT::EncodingType, typename ValueT::AllocatorType> MemberIterator; // This may be const or non-const iterator
2654  typedef GenericMemberIterator<true, typename ValueT::EncodingType, typename ValueT::AllocatorType> ConstMemberIterator;
2655  typedef typename ValueType::AllocatorType AllocatorType;
2656  typedef typename ValueType::StringRefType StringRefType;
2657  typedef typename ValueType::EncodingType EncodingType;
2658  typedef typename ValueType::Ch Ch;
2659 
2660  template <typename, typename>
2661  friend class GenericValue;
2662 
2663  GenericObject(const GenericObject& rhs) : value_(rhs.value_) {}
2664  GenericObject& operator=(const GenericObject& rhs) { value_ = rhs.value_; return *this; }
2665  ~GenericObject() {}
2666 
2667  SizeType MemberCount() const { return value_.MemberCount(); }
2668  SizeType MemberCapacity() const { return value_.MemberCapacity(); }
2669  bool ObjectEmpty() const { return value_.ObjectEmpty(); }
2670  template <typename T> ValueType& operator[](T* name) const { return value_[name]; }
2671  template <typename SourceAllocator> ValueType& operator[](const GenericValue<EncodingType, SourceAllocator>& name) const { return value_[name]; }
2672 #if RAPIDJSON_HAS_STDSTRING
2673  ValueType& operator[](const std::basic_string<Ch>& name) const { return value_[name]; }
2674 #endif
2675  MemberIterator MemberBegin() const { return value_.MemberBegin(); }
2676  MemberIterator MemberEnd() const { return value_.MemberEnd(); }
2677  GenericObject MemberReserve(SizeType newCapacity, AllocatorType &allocator) const { value_.MemberReserve(newCapacity, allocator); return *this; }
2678  bool HasMember(const Ch* name) const { return value_.HasMember(name); }
2679 #if RAPIDJSON_HAS_STDSTRING
2680  bool HasMember(const std::basic_string<Ch>& name) const { return value_.HasMember(name); }
2681 #endif
2682  template <typename SourceAllocator> bool HasMember(const GenericValue<EncodingType, SourceAllocator>& name) const { return value_.HasMember(name); }
2683  MemberIterator FindMember(const Ch* name) const { return value_.FindMember(name); }
2684  template <typename SourceAllocator> MemberIterator FindMember(const GenericValue<EncodingType, SourceAllocator>& name) const { return value_.FindMember(name); }
2685 #if RAPIDJSON_HAS_STDSTRING
2686  MemberIterator FindMember(const std::basic_string<Ch>& name) const { return value_.FindMember(name); }
2687 #endif
2688  GenericObject AddMember(ValueType& name, ValueType& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
2689  GenericObject AddMember(ValueType& name, StringRefType value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
2690 #if RAPIDJSON_HAS_STDSTRING
2691  GenericObject AddMember(ValueType& name, std::basic_string<Ch>& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
2692 #endif
2693  template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (ValueType&)) AddMember(ValueType& name, T value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
2694 #if RAPIDJSON_HAS_CXX11_RVALUE_REFS
2695  GenericObject AddMember(ValueType&& name, ValueType&& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
2696  GenericObject AddMember(ValueType&& name, ValueType& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
2697  GenericObject AddMember(ValueType& name, ValueType&& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
2698  GenericObject AddMember(StringRefType name, ValueType&& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
2699 #endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS
2700  GenericObject AddMember(StringRefType name, ValueType& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
2701  GenericObject AddMember(StringRefType name, StringRefType value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
2702  template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (GenericObject)) AddMember(StringRefType name, T value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
2703  void RemoveAllMembers() { value_.RemoveAllMembers(); }
2704  bool RemoveMember(const Ch* name) const { return value_.RemoveMember(name); }
2705 #if RAPIDJSON_HAS_STDSTRING
2706  bool RemoveMember(const std::basic_string<Ch>& name) const { return value_.RemoveMember(name); }
2707 #endif
2708  template <typename SourceAllocator> bool RemoveMember(const GenericValue<EncodingType, SourceAllocator>& name) const { return value_.RemoveMember(name); }
2709  MemberIterator RemoveMember(MemberIterator m) const { return value_.RemoveMember(m); }
2710  MemberIterator EraseMember(ConstMemberIterator pos) const { return value_.EraseMember(pos); }
2711  MemberIterator EraseMember(ConstMemberIterator first, ConstMemberIterator last) const { return value_.EraseMember(first, last); }
2712  bool EraseMember(const Ch* name) const { return value_.EraseMember(name); }
2713 #if RAPIDJSON_HAS_STDSTRING
2714  bool EraseMember(const std::basic_string<Ch>& name) const { return EraseMember(ValueType(StringRef(name))); }
2715 #endif
2716  template <typename SourceAllocator> bool EraseMember(const GenericValue<EncodingType, SourceAllocator>& name) const { return value_.EraseMember(name); }
2717 
2718 #if RAPIDJSON_HAS_CXX11_RANGE_FOR
2719  MemberIterator begin() const { return value_.MemberBegin(); }
2720  MemberIterator end() const { return value_.MemberEnd(); }
2721 #endif
2722 
2723 private:
2724  GenericObject();
2725  GenericObject(ValueType& value) : value_(value) {}
2726  ValueType& value_;
2727 };
2728 
2729 RAPIDJSON_NAMESPACE_END
2730 RAPIDJSON_DIAG_POP
2731 
2732 #endif // RAPIDJSON_DOCUMENT_H_
rapidjson::GenericValue::GenericValue
GenericValue(float f) RAPIDJSON_NOEXCEPT
Constructor for float value.
Definition: document.h:833
rapidjson::ParseResult
Result of parsing (wraps ParseErrorCode)
Definition: error.h:106
rapidjson::GenericValue
Represents a JSON value. Use Value for UTF8 encoding and default allocator.
Definition: document.h:57
rapidjson::GenericMemberIterator::operator-
DifferenceType operator-(ConstIterator that) const
Distance
Definition: document.h:273
rapidjson::GenericValue::String
Definition: document.h:2035
rapidjson::GenericArray
Helper class for accessing Value of array type.
Definition: document.h:640
rapidjson::GenericMemberIterator::GenericMemberIterator
GenericMemberIterator()
Default constructor (singular value)
Definition: document.h:213
rapidjson::GenericValue::StringRefType
GenericStringRef< Ch > StringRefType
Reference to a constant string
Definition: document.h:664
Allocator
Concept for allocating, resizing and freeing memory block.
rapidjson::GenericValue::operator=
GenericValue & operator=(GenericValue &rhs) RAPIDJSON_NOEXCEPT
Assignment with move semantics.
Definition: document.h:915
rapidjson::GenericValue::ValueIterator
GenericValue * ValueIterator
Value iterator for iterating in array.
Definition: document.h:667
rapidjson::GenericMemberIterator::Iterator
GenericMemberIterator Iterator
Iterator type itself
Definition: document.h:187
rapidjson::GenericInsituStringStream
A read-write string stream.
Definition: fwd.h:52
rapidjson::Type
Type
Type of JSON value
Definition: rapidjson.h:664
rapidjson::GenericDocument::ParseStream
GenericDocument & ParseStream(InputStream &is)
Parse JSON text from an input stream (with kParseDefaultFlags)
Definition: document.h:2367
rapidjson::GenericDocument::AllocatorType
Allocator AllocatorType
Allocator type from template parameter.
Definition: document.h:2207
rapidjson::GenericMemberIterator::Reference
reference Reference
Reference to (const) GenericMember
Definition: document.h:205
rapidjson::GenericValue::GenericValue
GenericValue(uint64_t u64) RAPIDJSON_NOEXCEPT
Constructor for uint64_t value.
Definition: document.h:818
rapidjson::GenericValue::GenericValue
GenericValue(Object o) RAPIDJSON_NOEXCEPT
Constructor for Object.
Definition: document.h:871
rapidjson::kTrueType
true
Definition: rapidjson.h:667
rapidjson::GenericDocument::ParseInsitu
GenericDocument & ParseInsitu(Ch *str)
Parse JSON text from a mutable string (with kParseDefaultFlags)
Definition: document.h:2390
rapidjson::EncodedInputStream
Input byte stream wrapper with a statically bound encoding.
Definition: encodedstream.h:39
rapidjson::GenericStringRef::StringRef
GenericStringRef< CharType > StringRef(const CharType *str)
Mark a character pointer as constant string
Definition: document.h:443
rapidjson::GenericValue::GenericValue
GenericValue(const Ch *s, SizeType length, Allocator &allocator)
Constructor for copy-string (i.e. do make a copy of string)
Definition: document.h:842
rapidjson::GenericValue::GenericValue
GenericValue(const std::basic_string< Ch > &s, Allocator &allocator)
Constructor for copy-string from a string object (i.e. do make a copy of string)
Definition: document.h:851
rapidjson::GenericMember::name
GenericValue< Encoding, Allocator > name
name of member (must be a string)
Definition: document.h:113
rapidjson::GenericDocument::GenericDocument
GenericDocument(Allocator *allocator=0, size_t stackCapacity=kDefaultStackCapacity, StackAllocator *stackAllocator=0)
Constructor
Definition: document.h:2229
rapidjson::GenericDocument::ValueType
GenericValue< Encoding, Allocator > ValueType
Value type of the document.
Definition: document.h:2206
rapidjson::GenericValue::GenericValue
GenericValue(StringRefType s) RAPIDJSON_NOEXCEPT
Constructor for constant string (i.e. do not make a copy of string)
Definition: document.h:839
rapidjson::GenericMemberIterator
(Constant) member iterator for a JSON object value
Definition: document.h:177
rapidjson::StringRef
GenericStringRef< CharType > StringRef(const std::basic_string< CharType > &str)
Mark a string object as constant string
Definition: document.h:481
rapidjson::GenericDocument::GetParseError
ParseErrorCode GetParseError() const
Get the ParseErrorCode of last parsing.
Definition: document.h:2470
rapidjson::GenericDocument::Parse
GenericDocument & Parse(const Ch *str)
Parse JSON text from a read-only string (with kParseDefaultFlags)
Definition: document.h:2422
rapidjson::MemoryStream
Represents an in-memory input byte stream.
Definition: memorystream.h:40
rapidjson::GenericValue::GenericValue
GenericValue(const GenericValue< Encoding, SourceAllocator > &rhs, Allocator &allocator, bool copyConstStrings=false)
Explicit copy constructor (with allocator)
Definition: document.h:731
rapidjson::GenericDocument::Parse
GenericDocument & Parse(const Ch *str)
Parse JSON text from a read-only string
Definition: document.h:2415
rapidjson::GenericValue::ArrayData
Definition: document.h:2090
rapidjson::GenericMemberIterator::Pointer
pointer Pointer
Pointer to (const) GenericMember
Definition: document.h:203
rapidjson::GenericValue::ObjectData
Definition: document.h:2084
rapidjson::GenericValue::GenericValue
GenericValue(const Ch *s, SizeType length) RAPIDJSON_NOEXCEPT
Constructor for constant string (i.e. do not make a copy of string)
Definition: document.h:836
rapidjson::GenericStringStream
Read-only string stream.
Definition: fwd.h:47
rapidjson::kFalseType
false
Definition: rapidjson.h:666
rapidjson::GenericValue::GenericValue
GenericValue(Array a) RAPIDJSON_NOEXCEPT
Constructor for Array.
Definition: document.h:860
rapidjson::GenericDocument::GetStackCapacity
size_t GetStackCapacity() const
Get the capacity of stack in bytes.
Definition: document.h:2497
rapidjson::GenericMemberIterator::GenericMemberIterator
GenericMemberIterator(const NonConstIterator &it)
Iterator conversions to more const
Definition: document.h:231
rapidjson::GenericDocument::ParseStream
GenericDocument & ParseStream(InputStream &is)
Parse JSON text from an input stream (with Encoding conversion)
Definition: document.h:2338
rapidjson::ParseErrorCode
ParseErrorCode
Error code of parsing.
Definition: error.h:64
rapidjson::kObjectType
object
Definition: rapidjson.h:668
rapidjson::GenericValue::RawAssign
void RawAssign(GenericValue &rhs) RAPIDJSON_NOEXCEPT
Assignment without calling destructor
Definition: document.h:2163
rapidjson::GenericDocument::Swap
GenericDocument & Swap(GenericDocument &rhs) RAPIDJSON_NOEXCEPT
Exchange the contents of this document with those of another.
Definition: document.h:2285
rapidjson::GenericMember
Name-value pair in a JSON object value.
Definition: document.h:111
rapidjson::SizeType
unsigned SizeType
Size type (for string lengths, array sizes, etc.)
Definition: rapidjson.h:384
rapidjson::GenericDocument::GenericDocument
GenericDocument(Type type, Allocator *allocator=0, size_t stackCapacity=kDefaultStackCapacity, StackAllocator *stackAllocator=0)
Constructor
Definition: document.h:2216
rapidjson::GenericValue::MemberIterator
GenericMemberIterator< false, Encoding, Allocator >::Iterator MemberIterator
Member iterator for iterating in object.
Definition: document.h:665
rapidjson::GenericValue::GenericValue
GenericValue(const Ch *s, Allocator &allocator)
Constructor for copy-string (i.e. do make a copy of string)
Definition: document.h:845
rapidjson::GenericMember::operator=
GenericMember & operator=(GenericMember &rhs) RAPIDJSON_NOEXCEPT
Assignment with move semantics.
Definition: document.h:133
rapidjson::GenericValue::SetStringRaw
void SetStringRaw(StringRefType s, Allocator &allocator)
Initialize this value as copy string with initial data, without calling destructor.
Definition: document.h:2146
rapidjson::GenericValue::ConstMemberIterator
GenericMemberIterator< true, Encoding, Allocator >::Iterator ConstMemberIterator
Constant member iterator for iterating in object.
Definition: document.h:666
rapidjson::GenericObject
Helper class for accessing Value of object type.
Definition: document.h:641
RAPIDJSON_ASSERT
#define RAPIDJSON_ASSERT(x)
Assertion.
Definition: rapidjson.h:406
rapidjson::GenericStringRef::length
const SizeType length
length of the string (excluding the trailing NULL terminator)
Definition: document.h:409
rapidjson::kArrayType
array
Definition: rapidjson.h:669
rapidjson::GenericValue::ShortString
Definition: document.h:2049
rapidjson::GenericValue::Member
GenericMember< Encoding, Allocator > Member
Name-value pair in an object.
Definition: document.h:660
rapidjson::GenericValue::~GenericValue
~GenericValue()
Destructor.
Definition: document.h:879
rapidjson::GenericValue::GenericValue
GenericValue(int64_t i64) RAPIDJSON_NOEXCEPT
Constructor for int64_t value.
Definition: document.h:803
rapidjson::GenericValue::Number::U
Definition: document.h:2074
rapidjson::GenericDocument::swap
friend void swap(GenericDocument &a, GenericDocument &b) RAPIDJSON_NOEXCEPT
free-standing swap function helper
Definition: document.h:2310
rapidjson::GenericDocument::GetAllocator
Allocator & GetAllocator()
Get the allocator of this document.
Definition: document.h:2491
rapidjson::kNullType
null
Definition: rapidjson.h:665
rapidjson::Pointer
GenericPointer< Value, CrtAllocator > Pointer
GenericPointer for Value (UTF-8, default allocator).
Definition: fwd.h:126
rapidjson::GenericReader
SAX-style JSON parser. Use Reader for UTF8 encoding and default allocator.
Definition: fwd.h:88
rapidjson::GenericValue::GenericValue
GenericValue() RAPIDJSON_NOEXCEPT
Default constructor creates a null value.
Definition: document.h:679
rapidjson::GenericMemberIterator::ConstIterator
GenericMemberIterator< true, Encoding, Allocator > ConstIterator
Constant iterator type
Definition: document.h:189
rapidjson::GenericValue::operator=
GenericValue & operator=(StringRefType str) RAPIDJSON_NOEXCEPT
Assignment of constant string reference (no copy)
Definition: document.h:935
rapidjson::GenericValue::SetObjectRaw
void SetObjectRaw(Member *members, SizeType count, Allocator &allocator)
Initialize this value as object with initial data, without calling destructor.
Definition: document.h:2126
rapidjson::Value
GenericValue< UTF8<> > Value
GenericValue with UTF8 encoding
Definition: document.h:2189
rapidjson::GenericMember::value
GenericValue< Encoding, Allocator > value
value of member.
Definition: document.h:114
rapidjson::GenericMemberIterator::NonConstIterator
GenericMemberIterator< false, Encoding, Allocator > NonConstIterator
Non-constant iterator type
Definition: document.h:191
rapidjson::GenericDocument::Parse
GenericDocument & Parse(const typename SourceEncoding::Ch *str)
Parse JSON text from a read-only string (with Encoding conversion)
Definition: document.h:2404
reader.h
rapidjson::GenericDocument::Ch
Encoding::Ch Ch
Character type derived from Encoding.
Definition: document.h:2205
rapidjson::GenericValue::GenericValue
GenericValue(int i) RAPIDJSON_NOEXCEPT
Constructor for int value.
Definition: document.h:791
rapidjson::GenericValue::GenericValue
GenericValue(bool b) RAPIDJSON_NOEXCEPT
Constructor for boolean value.
Definition: document.h:782
rapidjson::GenericValue::Ch
Encoding::Ch Ch
Character type derived from Encoding.
Definition: document.h:663
rapidjson::GenericDocument::Populate
GenericDocument & Populate(Generator &g)
Populate this document by a generator which produces SAX events.
Definition: document.h:2318
rapidjson::GenericStringRef::GenericStringRef
GenericStringRef(const CharType(&str)[N]) RAPIDJSON_NOEXCEPT
Create string reference from const character array
Definition: document.h:364
rapidjson::GenericDocument::ParseInsitu
GenericDocument & ParseInsitu(Ch *str)
Parse JSON text from a mutable string
Definition: document.h:2381
RAPIDJSON_VALUE_DEFAULT_ARRAY_CAPACITY
#define RAPIDJSON_VALUE_DEFAULT_ARRAY_CAPACITY
User defined kDefaultArrayCapacity value.
Definition: document.h:101
rapidjson::GenericValue::Number
Definition: document.h:2059
rapidjson::GenericValue::EncodingType
Encoding EncodingType
Encoding type from template parameter.
Definition: document.h:661
rapidjson::GenericStringRef
Reference to a constant string (not taking a copy)
Definition: document.h:335
rapidjson::GenericValue::AllocatorType
Allocator AllocatorType
Allocator type from template parameter.
Definition: document.h:662
rapidjson::kParseInsituFlag
In-situ(destructive) parsing.
Definition: reader.h:148
rapidjson::kStringType
string
Definition: rapidjson.h:670
rapidjson::GenericPointer
Represents a JSON Pointer. Use Pointer for UTF8 encoding and default allocator.
Definition: fwd.h:126
RAPIDJSON_NEW
#define RAPIDJSON_NEW(TypeName)
! customization point for global new
Definition: rapidjson.h:647
rapidjson::GenericDocument
A document for parsing JSON text as DOM.
Definition: document.h:60
RAPIDJSON_DELETE
#define RAPIDJSON_DELETE(x)
! customization point for global delete
Definition: rapidjson.h:651
rapidjson::GenericStringRef::s
const Ch *const s
plain CharType pointer
Definition: document.h:408
rapidjson::GenericDocument::ParseStream
GenericDocument & ParseStream(InputStream &is)
Parse JSON text from an input stream
Definition: document.h:2357
rapidjson::Document
GenericDocument< UTF8<> > Document
GenericDocument with UTF8 encoding
Definition: document.h:2585
RAPIDJSON_NOEXCEPT_ASSERT
#define RAPIDJSON_NOEXCEPT_ASSERT(x)
Assertion (in non-throwing contexts).
Definition: rapidjson.h:638
rapidjson::kNumberType
number
Definition: rapidjson.h:671
rapidjson::GenericValue::SetStringRaw
void SetStringRaw(StringRefType s) RAPIDJSON_NOEXCEPT
Initialize this value as constant string, without calling destructor.
Definition: document.h:2139
rapidjson::GenericDocument::GetErrorOffset
size_t GetErrorOffset() const
Get the position of last parsing error in input, 0 otherwise.
Definition: document.h:2473
rapidjson::GenericStringRef::GenericStringRef
GenericStringRef(const CharType *str, SizeType len)
Create constant string reference from pointer and length
Definition: document.h:400
RAPIDJSON_LIKELY
#define RAPIDJSON_LIKELY(x)
Compiler branching hint for expression with high probability to be true.
Definition: rapidjson.h:463
rapidjson::GenericStringRef::GenericStringRef
GenericStringRef(const CharType *str)
Explicitly create string reference from const character pointer
Definition: document.h:388
rapidjson::GenericValue::ValueType
GenericValue< Encoding, Allocator > ValueType
Value type of itself.
Definition: document.h:669
rapidjson::GenericValue::Number::I
Definition: document.h:2070
rapidjson::GenericDocument::HasParseError
bool HasParseError() const
Whether a parse error has occurred in the last parsing.
Definition: document.h:2467
rapidjson::GenericValue::GenericValue
GenericValue(unsigned u) RAPIDJSON_NOEXCEPT
Constructor for unsigned value.
Definition: document.h:797
rapidjson::GenericValue::ConstValueIterator
const typedef GenericValue * ConstValueIterator
Constant value iterator for iterating in array.
Definition: document.h:668
rapidjson::GenericStringRef::Ch
CharType Ch
character type of the string
Definition: document.h:336
RAPIDJSON_UNLIKELY
#define RAPIDJSON_UNLIKELY(x)
Compiler branching hint for expression with low probability to be true.
Definition: rapidjson.h:476
rapidjson::GenericValue::GenericValue
GenericValue(Type type) RAPIDJSON_NOEXCEPT
Constructor with JSON value type.
Definition: document.h:709
rapidjson::GenericMemberIterator::DifferenceType
difference_type DifferenceType
Signed integer type (e.g. ptrdiff_t)
Definition: document.h:207
Encoding
Concept for encoding of Unicode characters.
rapidjson::GenericValue::String::hashcode
SizeType hashcode
reserved
Definition: document.h:2037
rapidjson::GenericValue::GenericValue
GenericValue(double d) RAPIDJSON_NOEXCEPT
Constructor for double value.
Definition: document.h:830
rapidjson::GenericValue::Data
Definition: document.h:2096
RAPIDJSON_UINT64_C2
#define RAPIDJSON_UINT64_C2(high32, low32)
Construct a 64-bit literal by a pair of 32-bit integer.
Definition: rapidjson.h:289
rapidjson::GenericValue::Flag
Definition: document.h:2024
RAPIDJSON_VALUE_DEFAULT_OBJECT_CAPACITY
#define RAPIDJSON_VALUE_DEFAULT_OBJECT_CAPACITY
User defined kDefaultObjectCapacity value.
Definition: document.h:90
Handler
Concept for receiving events from GenericReader upon parsing. The functions return true if no error o...
RAPIDJSON_STATIC_ASSERT
#define RAPIDJSON_STATIC_ASSERT(x)
(Internal) macro to check for conditions at compile-time
Definition: rapidjson.h:445