JsonCpp project page JsonCpp home page

json_value.cpp
Go to the documentation of this file.
1 // Copyright 2007-2010 Baptiste Lepilleur
2 // Distributed under MIT license, or public domain if desired and
3 // recognized in your jurisdiction.
4 // See file LICENSE for detail or copy at http://jsoncpp.sourceforge.net/LICENSE
5 
6 #if !defined(JSON_IS_AMALGAMATION)
7 # include <json/value.h>
8 # include <json/writer.h>
9 # ifndef JSON_USE_SIMPLE_INTERNAL_ALLOCATOR
10 # include "json_batchallocator.h"
11 # endif // #ifndef JSON_USE_SIMPLE_INTERNAL_ALLOCATOR
12 #endif // if !defined(JSON_IS_AMALGAMATION)
13 #include <iostream>
14 #include <utility>
15 #include <stdexcept>
16 #include <cstring>
17 #include <cassert>
18 #ifdef JSON_USE_CPPTL
19 # include <cpptl/conststring.h>
20 #endif
21 #include <cstddef> // size_t
22 
23 #define JSON_ASSERT_UNREACHABLE assert( false )
24 #define JSON_ASSERT( condition ) assert( condition ); // @todo <= change this into an exception throw
25 #define JSON_FAIL_MESSAGE( message ) throw std::runtime_error( message );
26 #define JSON_ASSERT_MESSAGE( condition, message ) if (!( condition )) JSON_FAIL_MESSAGE( message )
27 
28 namespace Json {
29 
30 const Value Value::null;
31 const Int Value::minInt = Int( ~(UInt(-1)/2) );
32 const Int Value::maxInt = Int( UInt(-1)/2 );
33 const UInt Value::maxUInt = UInt(-1);
34 const Int64 Value::minInt64 = Int64( ~(UInt64(-1)/2) );
35 const Int64 Value::maxInt64 = Int64( UInt64(-1)/2 );
36 const UInt64 Value::maxUInt64 = UInt64(-1);
40 
41 
43 static const unsigned int unknown = (unsigned)-1;
44 
45 
53 static inline char *
54 duplicateStringValue( const char *value,
55  unsigned int length = unknown )
56 {
57  if ( length == unknown )
58  length = (unsigned int)strlen(value);
59  char *newString = static_cast<char *>( malloc( length + 1 ) );
60  JSON_ASSERT_MESSAGE( newString != 0, "Failed to allocate string value buffer" );
61  memcpy( newString, value, length );
62  newString[length] = 0;
63  return newString;
64 }
65 
66 
69 static inline void
70 releaseStringValue( char *value )
71 {
72  if ( value )
73  free( value );
74 }
75 
76 } // namespace Json
77 
78 
79 // //////////////////////////////////////////////////////////////////
80 // //////////////////////////////////////////////////////////////////
81 // //////////////////////////////////////////////////////////////////
82 // ValueInternals...
83 // //////////////////////////////////////////////////////////////////
84 // //////////////////////////////////////////////////////////////////
85 // //////////////////////////////////////////////////////////////////
86 #if !defined(JSON_IS_AMALGAMATION)
87 # ifdef JSON_VALUE_USE_INTERNAL_MAP
88 # include "json_internalarray.inl"
89 # include "json_internalmap.inl"
90 # endif // JSON_VALUE_USE_INTERNAL_MAP
91 
92 # include "json_valueiterator.inl"
93 #endif // if !defined(JSON_IS_AMALGAMATION)
94 
95 namespace Json {
96 
97 // //////////////////////////////////////////////////////////////////
98 // //////////////////////////////////////////////////////////////////
99 // //////////////////////////////////////////////////////////////////
100 // class Value::CommentInfo
101 // //////////////////////////////////////////////////////////////////
102 // //////////////////////////////////////////////////////////////////
103 // //////////////////////////////////////////////////////////////////
104 
105 
106 Value::CommentInfo::CommentInfo()
107  : comment_( 0 )
108 {
109 }
110 
111 Value::CommentInfo::~CommentInfo()
112 {
113  if ( comment_ )
114  releaseStringValue( comment_ );
115 }
116 
117 
118 void
119 Value::CommentInfo::setComment( const char *text )
120 {
121  if ( comment_ )
122  releaseStringValue( comment_ );
123  JSON_ASSERT( text != 0 );
124  JSON_ASSERT_MESSAGE( text[0]=='\0' || text[0]=='/', "Comments must start with /");
125  // It seems that /**/ style comments are acceptable as well.
126  comment_ = duplicateStringValue( text );
127 }
128 
129 
130 // //////////////////////////////////////////////////////////////////
131 // //////////////////////////////////////////////////////////////////
132 // //////////////////////////////////////////////////////////////////
133 // class Value::CZString
134 // //////////////////////////////////////////////////////////////////
135 // //////////////////////////////////////////////////////////////////
136 // //////////////////////////////////////////////////////////////////
137 # ifndef JSON_VALUE_USE_INTERNAL_MAP
138 
139 // Notes: index_ indicates if the string was allocated when
140 // a string is stored.
141 
142 Value::CZString::CZString( ArrayIndex index )
143  : cstr_( 0 )
144  , index_( index )
145 {
146 }
147 
148 Value::CZString::CZString( const char *cstr, DuplicationPolicy allocate )
149  : cstr_( allocate == duplicate ? duplicateStringValue(cstr)
150  : cstr )
151  , index_( allocate )
152 {
153 }
154 
155 Value::CZString::CZString( const CZString &other )
156 : cstr_( other.index_ != noDuplication && other.cstr_ != 0
157  ? duplicateStringValue( other.cstr_ )
158  : other.cstr_ )
159  , index_( other.cstr_ ? (other.index_ == noDuplication ? noDuplication : duplicate)
160  : other.index_ )
161 {
162 }
163 
164 Value::CZString::~CZString()
165 {
166  if ( cstr_ && index_ == duplicate )
167  releaseStringValue( const_cast<char *>( cstr_ ) );
168 }
169 
170 void
171 Value::CZString::swap( CZString &other )
172 {
173  std::swap( cstr_, other.cstr_ );
174  std::swap( index_, other.index_ );
175 }
176 
177 Value::CZString &
178 Value::CZString::operator =( const CZString &other )
179 {
180  CZString temp( other );
181  swap( temp );
182  return *this;
183 }
184 
185 bool
186 Value::CZString::operator<( const CZString &other ) const
187 {
188  if ( cstr_ )
189  return strcmp( cstr_, other.cstr_ ) < 0;
190  return index_ < other.index_;
191 }
192 
193 bool
194 Value::CZString::operator==( const CZString &other ) const
195 {
196  if ( cstr_ )
197  return strcmp( cstr_, other.cstr_ ) == 0;
198  return index_ == other.index_;
199 }
200 
201 
202 ArrayIndex
203 Value::CZString::index() const
204 {
205  return index_;
206 }
207 
208 
209 const char *
210 Value::CZString::c_str() const
211 {
212  return cstr_;
213 }
214 
215 bool
216 Value::CZString::isStaticString() const
217 {
218  return index_ == noDuplication;
219 }
220 
221 #endif // ifndef JSON_VALUE_USE_INTERNAL_MAP
222 
223 
224 // //////////////////////////////////////////////////////////////////
225 // //////////////////////////////////////////////////////////////////
226 // //////////////////////////////////////////////////////////////////
227 // class Value::Value
228 // //////////////////////////////////////////////////////////////////
229 // //////////////////////////////////////////////////////////////////
230 // //////////////////////////////////////////////////////////////////
231 
236 Value::Value( ValueType type )
237  : type_( type )
238  , allocated_( 0 )
239  , comments_( 0 )
240 # ifdef JSON_VALUE_USE_INTERNAL_MAP
241  , itemIsUsed_( 0 )
242 #endif
243 {
244  switch ( type )
245  {
246  case nullValue:
247  break;
248  case intValue:
249  case uintValue:
250  value_.int_ = 0;
251  break;
252  case realValue:
253  value_.real_ = 0.0;
254  break;
255  case stringValue:
256  value_.string_ = 0;
257  break;
258 #ifndef JSON_VALUE_USE_INTERNAL_MAP
259  case arrayValue:
260  case objectValue:
261  value_.map_ = new ObjectValues();
262  break;
263 #else
264  case arrayValue:
265  value_.array_ = arrayAllocator()->newArray();
266  break;
267  case objectValue:
268  value_.map_ = mapAllocator()->newMap();
269  break;
270 #endif
271  case booleanValue:
272  value_.bool_ = false;
273  break;
274  default:
276  }
277 }
278 
279 
280 #if defined(JSON_HAS_INT64)
282  : type_( uintValue )
283  , comments_( 0 )
284 # ifdef JSON_VALUE_USE_INTERNAL_MAP
285  , itemIsUsed_( 0 )
286 #endif
287 {
288  value_.uint_ = value;
289 }
290 
292  : type_( intValue )
293  , comments_( 0 )
294 # ifdef JSON_VALUE_USE_INTERNAL_MAP
295  , itemIsUsed_( 0 )
296 #endif
297 {
298  value_.int_ = value;
299 }
300 
301 #endif // if defined(JSON_HAS_INT64)
302 
303 
305  : type_( intValue )
306  , comments_( 0 )
307 # ifdef JSON_VALUE_USE_INTERNAL_MAP
308  , itemIsUsed_( 0 )
309 #endif
310 {
311  value_.int_ = value;
312 }
313 
314 
316  : type_( uintValue )
317  , comments_( 0 )
318 # ifdef JSON_VALUE_USE_INTERNAL_MAP
319  , itemIsUsed_( 0 )
320 #endif
321 {
322  value_.uint_ = value;
323 }
324 
325 Value::Value( double value )
326  : type_( realValue )
327  , comments_( 0 )
328 # ifdef JSON_VALUE_USE_INTERNAL_MAP
329  , itemIsUsed_( 0 )
330 #endif
331 {
332  value_.real_ = value;
333 }
334 
335 Value::Value( const char *value )
336  : type_( stringValue )
337  , allocated_( true )
338  , comments_( 0 )
339 # ifdef JSON_VALUE_USE_INTERNAL_MAP
340  , itemIsUsed_( 0 )
341 #endif
342 {
343  value_.string_ = duplicateStringValue( value );
344 }
345 
346 
347 Value::Value( const char *beginValue,
348  const char *endValue )
349  : type_( stringValue )
350  , allocated_( true )
351  , comments_( 0 )
352 # ifdef JSON_VALUE_USE_INTERNAL_MAP
353  , itemIsUsed_( 0 )
354 #endif
355 {
356  value_.string_ = duplicateStringValue( beginValue,
357  (unsigned int)(endValue - beginValue) );
358 }
359 
360 
361 Value::Value( const std::string &value )
362  : type_( stringValue )
363  , allocated_( true )
364  , comments_( 0 )
365 # ifdef JSON_VALUE_USE_INTERNAL_MAP
366  , itemIsUsed_( 0 )
367 #endif
368 {
369  value_.string_ = duplicateStringValue( value.c_str(),
370  (unsigned int)value.length() );
371 
372 }
373 
374 Value::Value( const StaticString &value )
375  : type_( stringValue )
376  , allocated_( false )
377  , comments_( 0 )
378 # ifdef JSON_VALUE_USE_INTERNAL_MAP
379  , itemIsUsed_( 0 )
380 #endif
381 {
382  value_.string_ = const_cast<char *>( value.c_str() );
383 }
384 
385 
386 # ifdef JSON_USE_CPPTL
387 Value::Value( const CppTL::ConstString &value )
388  : type_( stringValue )
389  , allocated_( true )
390  , comments_( 0 )
391 # ifdef JSON_VALUE_USE_INTERNAL_MAP
392  , itemIsUsed_( 0 )
393 #endif
394 {
395  value_.string_ = duplicateStringValue( value, value.length() );
396 }
397 # endif
398 
399 Value::Value( bool value )
400  : type_( booleanValue )
401  , comments_( 0 )
402 # ifdef JSON_VALUE_USE_INTERNAL_MAP
403  , itemIsUsed_( 0 )
404 #endif
405 {
406  value_.bool_ = value;
407 }
408 
409 
410 Value::Value( const Value &other )
411  : type_( other.type_ )
412  , comments_( 0 )
413 # ifdef JSON_VALUE_USE_INTERNAL_MAP
414  , itemIsUsed_( 0 )
415 #endif
416 {
417  switch ( type_ )
418  {
419  case nullValue:
420  case intValue:
421  case uintValue:
422  case realValue:
423  case booleanValue:
424  value_ = other.value_;
425  break;
426  case stringValue:
427  if ( other.value_.string_ )
428  {
429  value_.string_ = duplicateStringValue( other.value_.string_ );
430  allocated_ = true;
431  }
432  else
433  value_.string_ = 0;
434  break;
435 #ifndef JSON_VALUE_USE_INTERNAL_MAP
436  case arrayValue:
437  case objectValue:
438  value_.map_ = new ObjectValues( *other.value_.map_ );
439  break;
440 #else
441  case arrayValue:
442  value_.array_ = arrayAllocator()->newArrayCopy( *other.value_.array_ );
443  break;
444  case objectValue:
445  value_.map_ = mapAllocator()->newMapCopy( *other.value_.map_ );
446  break;
447 #endif
448  default:
450  }
451  if ( other.comments_ )
452  {
453  comments_ = new CommentInfo[numberOfCommentPlacement];
454  for ( int comment =0; comment < numberOfCommentPlacement; ++comment )
455  {
456  const CommentInfo &otherComment = other.comments_[comment];
457  if ( otherComment.comment_ )
458  comments_[comment].setComment( otherComment.comment_ );
459  }
460  }
461 }
462 
463 
465 {
466  switch ( type_ )
467  {
468  case nullValue:
469  case intValue:
470  case uintValue:
471  case realValue:
472  case booleanValue:
473  break;
474  case stringValue:
475  if ( allocated_ )
476  releaseStringValue( value_.string_ );
477  break;
478 #ifndef JSON_VALUE_USE_INTERNAL_MAP
479  case arrayValue:
480  case objectValue:
481  delete value_.map_;
482  break;
483 #else
484  case arrayValue:
485  arrayAllocator()->destructArray( value_.array_ );
486  break;
487  case objectValue:
488  mapAllocator()->destructMap( value_.map_ );
489  break;
490 #endif
491  default:
493  }
494 
495  if ( comments_ )
496  delete[] comments_;
497 }
498 
499 Value &
500 Value::operator=( const Value &other )
501 {
502  Value temp( other );
503  swap( temp );
504  return *this;
505 }
506 
507 void
509 {
510  ValueType temp = type_;
511  type_ = other.type_;
512  other.type_ = temp;
513  std::swap( value_, other.value_ );
514  int temp2 = allocated_;
515  allocated_ = other.allocated_;
516  other.allocated_ = temp2;
517 }
518 
519 ValueType
520 Value::type() const
521 {
522  return type_;
523 }
524 
525 
526 int
527 Value::compare( const Value &other ) const
528 {
529  if ( *this < other )
530  return -1;
531  if ( *this > other )
532  return 1;
533  return 0;
534 }
535 
536 
537 bool
538 Value::operator <( const Value &other ) const
539 {
540  int typeDelta = type_ - other.type_;
541  if ( typeDelta )
542  return typeDelta < 0 ? true : false;
543  switch ( type_ )
544  {
545  case nullValue:
546  return false;
547  case intValue:
548  return value_.int_ < other.value_.int_;
549  case uintValue:
550  return value_.uint_ < other.value_.uint_;
551  case realValue:
552  return value_.real_ < other.value_.real_;
553  case booleanValue:
554  return value_.bool_ < other.value_.bool_;
555  case stringValue:
556  return ( value_.string_ == 0 && other.value_.string_ )
557  || ( other.value_.string_
558  && value_.string_
559  && strcmp( value_.string_, other.value_.string_ ) < 0 );
560 #ifndef JSON_VALUE_USE_INTERNAL_MAP
561  case arrayValue:
562  case objectValue:
563  {
564  int delta = int( value_.map_->size() - other.value_.map_->size() );
565  if ( delta )
566  return delta < 0;
567  return (*value_.map_) < (*other.value_.map_);
568  }
569 #else
570  case arrayValue:
571  return value_.array_->compare( *(other.value_.array_) ) < 0;
572  case objectValue:
573  return value_.map_->compare( *(other.value_.map_) ) < 0;
574 #endif
575  default:
577  }
578  return false; // unreachable
579 }
580 
581 bool
582 Value::operator <=( const Value &other ) const
583 {
584  return !(other < *this);
585 }
586 
587 bool
588 Value::operator >=( const Value &other ) const
589 {
590  return !(*this < other);
591 }
592 
593 bool
594 Value::operator >( const Value &other ) const
595 {
596  return other < *this;
597 }
598 
599 bool
600 Value::operator ==( const Value &other ) const
601 {
602  //if ( type_ != other.type_ )
603  // GCC 2.95.3 says:
604  // attempt to take address of bit-field structure member `Json::Value::type_'
605  // Beats me, but a temp solves the problem.
606  int temp = other.type_;
607  if ( type_ != temp )
608  return false;
609  switch ( type_ )
610  {
611  case nullValue:
612  return true;
613  case intValue:
614  return value_.int_ == other.value_.int_;
615  case uintValue:
616  return value_.uint_ == other.value_.uint_;
617  case realValue:
618  return value_.real_ == other.value_.real_;
619  case booleanValue:
620  return value_.bool_ == other.value_.bool_;
621  case stringValue:
622  return ( value_.string_ == other.value_.string_ )
623  || ( other.value_.string_
624  && value_.string_
625  && strcmp( value_.string_, other.value_.string_ ) == 0 );
626 #ifndef JSON_VALUE_USE_INTERNAL_MAP
627  case arrayValue:
628  case objectValue:
629  return value_.map_->size() == other.value_.map_->size()
630  && (*value_.map_) == (*other.value_.map_);
631 #else
632  case arrayValue:
633  return value_.array_->compare( *(other.value_.array_) ) == 0;
634  case objectValue:
635  return value_.map_->compare( *(other.value_.map_) ) == 0;
636 #endif
637  default:
639  }
640  return false; // unreachable
641 }
642 
643 bool
644 Value::operator !=( const Value &other ) const
645 {
646  return !( *this == other );
647 }
648 
649 const char *
651 {
652  JSON_ASSERT( type_ == stringValue );
653  return value_.string_;
654 }
655 
656 
657 std::string
659 {
660  switch ( type_ )
661  {
662  case nullValue:
663  return "";
664  case stringValue:
665  return value_.string_ ? value_.string_ : "";
666  case booleanValue:
667  return value_.bool_ ? "true" : "false";
668  case intValue:
669  case uintValue:
670  case realValue:
671  case arrayValue:
672  case objectValue:
673  JSON_FAIL_MESSAGE( "Type is not convertible to string" );
674  default:
676  }
677  return ""; // unreachable
678 }
679 
680 # ifdef JSON_USE_CPPTL
681 CppTL::ConstString
682 Value::asConstString() const
683 {
684  return CppTL::ConstString( asString().c_str() );
685 }
686 # endif
687 
688 
689 Value::Int
691 {
692  switch ( type_ )
693  {
694  case nullValue:
695  return 0;
696  case intValue:
697  JSON_ASSERT_MESSAGE( value_.int_ >= minInt && value_.int_ <= maxInt, "unsigned integer out of signed int range" );
698  return Int(value_.int_);
699  case uintValue:
700  JSON_ASSERT_MESSAGE( value_.uint_ <= UInt(maxInt), "unsigned integer out of signed int range" );
701  return Int(value_.uint_);
702  case realValue:
703  JSON_ASSERT_MESSAGE( value_.real_ >= minInt && value_.real_ <= maxInt, "Real out of signed integer range" );
704  return Int( value_.real_ );
705  case booleanValue:
706  return value_.bool_ ? 1 : 0;
707  case stringValue:
708  case arrayValue:
709  case objectValue:
710  JSON_FAIL_MESSAGE( "Type is not convertible to int" );
711  default:
713  }
714  return 0; // unreachable;
715 }
716 
717 
720 {
721  switch ( type_ )
722  {
723  case nullValue:
724  return 0;
725  case intValue:
726  JSON_ASSERT_MESSAGE( value_.int_ >= 0, "Negative integer can not be converted to unsigned integer" );
727  JSON_ASSERT_MESSAGE( value_.int_ <= maxUInt, "signed integer out of UInt range" );
728  return UInt(value_.int_);
729  case uintValue:
730  JSON_ASSERT_MESSAGE( value_.uint_ <= maxUInt, "unsigned integer out of UInt range" );
731  return UInt(value_.uint_);
732  case realValue:
733  JSON_ASSERT_MESSAGE( value_.real_ >= 0 && value_.real_ <= maxUInt, "Real out of unsigned integer range" );
734  return UInt( value_.real_ );
735  case booleanValue:
736  return value_.bool_ ? 1 : 0;
737  case stringValue:
738  case arrayValue:
739  case objectValue:
740  JSON_FAIL_MESSAGE( "Type is not convertible to uint" );
741  default:
743  }
744  return 0; // unreachable;
745 }
746 
747 
748 # if defined(JSON_HAS_INT64)
749 
752 {
753  switch ( type_ )
754  {
755  case nullValue:
756  return 0;
757  case intValue:
758  return value_.int_;
759  case uintValue:
760  JSON_ASSERT_MESSAGE( value_.uint_ <= UInt64(maxInt64), "unsigned integer out of Int64 range" );
761  return value_.uint_;
762  case realValue:
763  JSON_ASSERT_MESSAGE( value_.real_ >= minInt64 && value_.real_ <= maxInt64, "Real out of Int64 range" );
764  return Int( value_.real_ );
765  case booleanValue:
766  return value_.bool_ ? 1 : 0;
767  case stringValue:
768  case arrayValue:
769  case objectValue:
770  JSON_FAIL_MESSAGE( "Type is not convertible to Int64" );
771  default:
773  }
774  return 0; // unreachable;
775 }
776 
777 
780 {
781  switch ( type_ )
782  {
783  case nullValue:
784  return 0;
785  case intValue:
786  JSON_ASSERT_MESSAGE( value_.int_ >= 0, "Negative integer can not be converted to UInt64" );
787  return value_.int_;
788  case uintValue:
789  return value_.uint_;
790  case realValue:
791  JSON_ASSERT_MESSAGE( value_.real_ >= 0 && value_.real_ <= maxUInt64, "Real out of UInt64 range" );
792  return UInt( value_.real_ );
793  case booleanValue:
794  return value_.bool_ ? 1 : 0;
795  case stringValue:
796  case arrayValue:
797  case objectValue:
798  JSON_FAIL_MESSAGE( "Type is not convertible to UInt64" );
799  default:
801  }
802  return 0; // unreachable;
803 }
804 # endif // if defined(JSON_HAS_INT64)
805 
806 
807 LargestInt
809 {
810 #if defined(JSON_NO_INT64)
811  return asInt();
812 #else
813  return asInt64();
814 #endif
815 }
816 
817 
820 {
821 #if defined(JSON_NO_INT64)
822  return asUInt();
823 #else
824  return asUInt64();
825 #endif
826 }
827 
828 
829 double
831 {
832  switch ( type_ )
833  {
834  case nullValue:
835  return 0.0;
836  case intValue:
837  return static_cast<double>( value_.int_ );
838  case uintValue:
839 #if !defined(JSON_USE_INT64_DOUBLE_CONVERSION)
840  return static_cast<double>( value_.uint_ );
841 #else // if !defined(JSON_USE_INT64_DOUBLE_CONVERSION)
842  return static_cast<double>( Int(value_.uint_/2) ) * 2 + Int(value_.uint_ & 1);
843 #endif // if !defined(JSON_USE_INT64_DOUBLE_CONVERSION)
844  case realValue:
845  return value_.real_;
846  case booleanValue:
847  return value_.bool_ ? 1.0 : 0.0;
848  case stringValue:
849  case arrayValue:
850  case objectValue:
851  JSON_FAIL_MESSAGE( "Type is not convertible to double" );
852  default:
854  }
855  return 0; // unreachable;
856 }
857 
858 float
860 {
861  switch ( type_ )
862  {
863  case nullValue:
864  return 0.0f;
865  case intValue:
866  return static_cast<float>( value_.int_ );
867  case uintValue:
868 #if !defined(JSON_USE_INT64_DOUBLE_CONVERSION)
869  return static_cast<float>( value_.uint_ );
870 #else // if !defined(JSON_USE_INT64_DOUBLE_CONVERSION)
871  return static_cast<float>( Int(value_.uint_/2) ) * 2 + Int(value_.uint_ & 1);
872 #endif // if !defined(JSON_USE_INT64_DOUBLE_CONVERSION)
873  case realValue:
874  return static_cast<float>( value_.real_ );
875  case booleanValue:
876  return value_.bool_ ? 1.0f : 0.0f;
877  case stringValue:
878  case arrayValue:
879  case objectValue:
880  JSON_FAIL_MESSAGE( "Type is not convertible to float" );
881  default:
883  }
884  return 0.0f; // unreachable;
885 }
886 
887 bool
889 {
890  switch ( type_ )
891  {
892  case nullValue:
893  return false;
894  case intValue:
895  case uintValue:
896  return value_.int_ != 0;
897  case realValue:
898  return value_.real_ != 0.0;
899  case booleanValue:
900  return value_.bool_;
901  case stringValue:
902  return value_.string_ && value_.string_[0] != 0;
903  case arrayValue:
904  case objectValue:
905  return value_.map_->size() != 0;
906  default:
908  }
909  return false; // unreachable;
910 }
911 
912 
913 bool
915 {
916  switch ( type_ )
917  {
918  case nullValue:
919  return true;
920  case intValue:
921  return ( other == nullValue && value_.int_ == 0 )
922  || other == intValue
923  || ( other == uintValue && value_.int_ >= 0 )
924  || other == realValue
925  || other == stringValue
926  || other == booleanValue;
927  case uintValue:
928  return ( other == nullValue && value_.uint_ == 0 )
929  || ( other == intValue && value_.uint_ <= (unsigned)maxInt )
930  || other == uintValue
931  || other == realValue
932  || other == stringValue
933  || other == booleanValue;
934  case realValue:
935  return ( other == nullValue && value_.real_ == 0.0 )
936  || ( other == intValue && value_.real_ >= minInt && value_.real_ <= maxInt )
937  || ( other == uintValue && value_.real_ >= 0 && value_.real_ <= maxUInt )
938  || other == realValue
939  || other == stringValue
940  || other == booleanValue;
941  case booleanValue:
942  return ( other == nullValue && value_.bool_ == false )
943  || other == intValue
944  || other == uintValue
945  || other == realValue
946  || other == stringValue
947  || other == booleanValue;
948  case stringValue:
949  return other == stringValue
950  || ( other == nullValue && (!value_.string_ || value_.string_[0] == 0) );
951  case arrayValue:
952  return other == arrayValue
953  || ( other == nullValue && value_.map_->size() == 0 );
954  case objectValue:
955  return other == objectValue
956  || ( other == nullValue && value_.map_->size() == 0 );
957  default:
959  }
960  return false; // unreachable;
961 }
962 
963 
965 ArrayIndex
966 Value::size() const
967 {
968  switch ( type_ )
969  {
970  case nullValue:
971  case intValue:
972  case uintValue:
973  case realValue:
974  case booleanValue:
975  case stringValue:
976  return 0;
977 #ifndef JSON_VALUE_USE_INTERNAL_MAP
978  case arrayValue: // size of the array is highest index + 1
979  if ( !value_.map_->empty() )
980  {
981  ObjectValues::const_iterator itLast = value_.map_->end();
982  --itLast;
983  return (*itLast).first.index()+1;
984  }
985  return 0;
986  case objectValue:
987  return ArrayIndex( value_.map_->size() );
988 #else
989  case arrayValue:
990  return Int( value_.array_->size() );
991  case objectValue:
992  return Int( value_.map_->size() );
993 #endif
994  default:
996  }
997  return 0; // unreachable;
998 }
999 
1000 
1001 bool
1003 {
1004  if ( isNull() || isArray() || isObject() )
1005  return size() == 0u;
1006  else
1007  return false;
1008 }
1009 
1010 
1011 bool
1013 {
1014  return isNull();
1015 }
1016 
1017 
1018 void
1020 {
1021  JSON_ASSERT( type_ == nullValue || type_ == arrayValue || type_ == objectValue );
1022 
1023  switch ( type_ )
1024  {
1025 #ifndef JSON_VALUE_USE_INTERNAL_MAP
1026  case arrayValue:
1027  case objectValue:
1028  value_.map_->clear();
1029  break;
1030 #else
1031  case arrayValue:
1032  value_.array_->clear();
1033  break;
1034  case objectValue:
1035  value_.map_->clear();
1036  break;
1037 #endif
1038  default:
1039  break;
1040  }
1041 }
1042 
1043 void
1045 {
1046  JSON_ASSERT( type_ == nullValue || type_ == arrayValue );
1047  if ( type_ == nullValue )
1048  *this = Value( arrayValue );
1049 #ifndef JSON_VALUE_USE_INTERNAL_MAP
1050  ArrayIndex oldSize = size();
1051  if ( newSize == 0 )
1052  clear();
1053  else if ( newSize > oldSize )
1054  (*this)[ newSize - 1 ];
1055  else
1056  {
1057  for ( ArrayIndex index = newSize; index < oldSize; ++index )
1058  {
1059  value_.map_->erase( index );
1060  }
1061  assert( size() == newSize );
1062  }
1063 #else
1064  value_.array_->resize( newSize );
1065 #endif
1066 }
1067 
1068 
1069 Value &
1071 {
1072  JSON_ASSERT( type_ == nullValue || type_ == arrayValue );
1073  if ( type_ == nullValue )
1074  *this = Value( arrayValue );
1075 #ifndef JSON_VALUE_USE_INTERNAL_MAP
1076  CZString key( index );
1077  ObjectValues::iterator it = value_.map_->lower_bound( key );
1078  if ( it != value_.map_->end() && (*it).first == key )
1079  return (*it).second;
1080 
1081  ObjectValues::value_type defaultValue( key, null );
1082  it = value_.map_->insert( it, defaultValue );
1083  return (*it).second;
1084 #else
1085  return value_.array_->resolveReference( index );
1086 #endif
1087 }
1088 
1089 
1090 Value &
1091 Value::operator[]( int index )
1092 {
1093  JSON_ASSERT( index >= 0 );
1094  return (*this)[ ArrayIndex(index) ];
1095 }
1096 
1097 
1098 const Value &
1100 {
1101  JSON_ASSERT( type_ == nullValue || type_ == arrayValue );
1102  if ( type_ == nullValue )
1103  return null;
1104 #ifndef JSON_VALUE_USE_INTERNAL_MAP
1105  CZString key( index );
1106  ObjectValues::const_iterator it = value_.map_->find( key );
1107  if ( it == value_.map_->end() )
1108  return null;
1109  return (*it).second;
1110 #else
1111  Value *value = value_.array_->find( index );
1112  return value ? *value : null;
1113 #endif
1114 }
1115 
1116 
1117 const Value &
1118 Value::operator[]( int index ) const
1119 {
1120  JSON_ASSERT( index >= 0 );
1121  return (*this)[ ArrayIndex(index) ];
1122 }
1123 
1124 
1125 Value &
1126 Value::operator[]( const char *key )
1127 {
1128  return resolveReference( key, false );
1129 }
1130 
1131 
1132 Value &
1133 Value::resolveReference( const char *key,
1134  bool isStatic )
1135 {
1136  JSON_ASSERT( type_ == nullValue || type_ == objectValue );
1137  if ( type_ == nullValue )
1138  *this = Value( objectValue );
1139 #ifndef JSON_VALUE_USE_INTERNAL_MAP
1140  CZString actualKey( key, isStatic ? CZString::noDuplication
1141  : CZString::duplicateOnCopy );
1142  ObjectValues::iterator it = value_.map_->lower_bound( actualKey );
1143  if ( it != value_.map_->end() && (*it).first == actualKey )
1144  return (*it).second;
1145 
1146  ObjectValues::value_type defaultValue( actualKey, null );
1147  it = value_.map_->insert( it, defaultValue );
1148  Value &value = (*it).second;
1149  return value;
1150 #else
1151  return value_.map_->resolveReference( key, isStatic );
1152 #endif
1153 }
1154 
1155 
1156 Value
1158  const Value &defaultValue ) const
1159 {
1160  const Value *value = &((*this)[index]);
1161  return value == &null ? defaultValue : *value;
1162 }
1163 
1164 
1165 bool
1167 {
1168  return index < size();
1169 }
1170 
1171 
1172 
1173 const Value &
1174 Value::operator[]( const char *key ) const
1175 {
1176  JSON_ASSERT( type_ == nullValue || type_ == objectValue );
1177  if ( type_ == nullValue )
1178  return null;
1179 #ifndef JSON_VALUE_USE_INTERNAL_MAP
1180  CZString actualKey( key, CZString::noDuplication );
1181  ObjectValues::const_iterator it = value_.map_->find( actualKey );
1182  if ( it == value_.map_->end() )
1183  return null;
1184  return (*it).second;
1185 #else
1186  const Value *value = value_.map_->find( key );
1187  return value ? *value : null;
1188 #endif
1189 }
1190 
1191 
1192 Value &
1193 Value::operator[]( const std::string &key )
1194 {
1195  return (*this)[ key.c_str() ];
1196 }
1197 
1198 
1199 const Value &
1200 Value::operator[]( const std::string &key ) const
1201 {
1202  return (*this)[ key.c_str() ];
1203 }
1204 
1205 Value &
1207 {
1208  return resolveReference( key, true );
1209 }
1210 
1211 
1212 # ifdef JSON_USE_CPPTL
1213 Value &
1214 Value::operator[]( const CppTL::ConstString &key )
1215 {
1216  return (*this)[ key.c_str() ];
1217 }
1218 
1219 
1220 const Value &
1221 Value::operator[]( const CppTL::ConstString &key ) const
1222 {
1223  return (*this)[ key.c_str() ];
1224 }
1225 # endif
1226 
1227 
1228 Value &
1229 Value::append( const Value &value )
1230 {
1231  return (*this)[size()] = value;
1232 }
1233 
1234 
1235 Value
1236 Value::get( const char *key,
1237  const Value &defaultValue ) const
1238 {
1239  const Value *value = &((*this)[key]);
1240  return value == &null ? defaultValue : *value;
1241 }
1242 
1243 
1244 Value
1245 Value::get( const std::string &key,
1246  const Value &defaultValue ) const
1247 {
1248  return get( key.c_str(), defaultValue );
1249 }
1250 
1251 Value
1252 Value::removeMember( const char* key )
1253 {
1254  JSON_ASSERT( type_ == nullValue || type_ == objectValue );
1255  if ( type_ == nullValue )
1256  return null;
1257 #ifndef JSON_VALUE_USE_INTERNAL_MAP
1258  CZString actualKey( key, CZString::noDuplication );
1259  ObjectValues::iterator it = value_.map_->find( actualKey );
1260  if ( it == value_.map_->end() )
1261  return null;
1262  Value old(it->second);
1263  value_.map_->erase(it);
1264  return old;
1265 #else
1266  Value *value = value_.map_->find( key );
1267  if (value){
1268  Value old(*value);
1269  value_.map_.remove( key );
1270  return old;
1271  } else {
1272  return null;
1273  }
1274 #endif
1275 }
1276 
1277 Value
1278 Value::removeMember( const std::string &key )
1279 {
1280  return removeMember( key.c_str() );
1281 }
1282 
1283 # ifdef JSON_USE_CPPTL
1284 Value
1285 Value::get( const CppTL::ConstString &key,
1286  const Value &defaultValue ) const
1287 {
1288  return get( key.c_str(), defaultValue );
1289 }
1290 # endif
1291 
1292 bool
1293 Value::isMember( const char *key ) const
1294 {
1295  const Value *value = &((*this)[key]);
1296  return value != &null;
1297 }
1298 
1299 
1300 bool
1301 Value::isMember( const std::string &key ) const
1302 {
1303  return isMember( key.c_str() );
1304 }
1305 
1306 
1307 # ifdef JSON_USE_CPPTL
1308 bool
1309 Value::isMember( const CppTL::ConstString &key ) const
1310 {
1311  return isMember( key.c_str() );
1312 }
1313 #endif
1314 
1317 {
1318  JSON_ASSERT( type_ == nullValue || type_ == objectValue );
1319  if ( type_ == nullValue )
1320  return Value::Members();
1321  Members members;
1322  members.reserve( value_.map_->size() );
1323 #ifndef JSON_VALUE_USE_INTERNAL_MAP
1324  ObjectValues::const_iterator it = value_.map_->begin();
1325  ObjectValues::const_iterator itEnd = value_.map_->end();
1326  for ( ; it != itEnd; ++it )
1327  members.push_back( std::string( (*it).first.c_str() ) );
1328 #else
1329  ValueInternalMap::IteratorState it;
1330  ValueInternalMap::IteratorState itEnd;
1331  value_.map_->makeBeginIterator( it );
1332  value_.map_->makeEndIterator( itEnd );
1333  for ( ; !ValueInternalMap::equals( it, itEnd ); ValueInternalMap::increment(it) )
1334  members.push_back( std::string( ValueInternalMap::key( it ) ) );
1335 #endif
1336  return members;
1337 }
1338 //
1339 //# ifdef JSON_USE_CPPTL
1340 //EnumMemberNames
1341 //Value::enumMemberNames() const
1342 //{
1343 // if ( type_ == objectValue )
1344 // {
1345 // return CppTL::Enum::any( CppTL::Enum::transform(
1346 // CppTL::Enum::keys( *(value_.map_), CppTL::Type<const CZString &>() ),
1347 // MemberNamesTransform() ) );
1348 // }
1349 // return EnumMemberNames();
1350 //}
1351 //
1352 //
1353 //EnumValues
1354 //Value::enumValues() const
1355 //{
1356 // if ( type_ == objectValue || type_ == arrayValue )
1357 // return CppTL::Enum::anyValues( *(value_.map_),
1358 // CppTL::Type<const Value &>() );
1359 // return EnumValues();
1360 //}
1361 //
1362 //# endif
1363 
1364 
1365 bool
1367 {
1368  return type_ == nullValue;
1369 }
1370 
1371 
1372 bool
1374 {
1375  return type_ == booleanValue;
1376 }
1377 
1378 
1379 bool
1381 {
1382  return type_ == intValue;
1383 }
1384 
1385 
1386 bool
1388 {
1389  return type_ == uintValue;
1390 }
1391 
1392 
1393 bool
1395 {
1396  return type_ == intValue
1397  || type_ == uintValue
1398  || type_ == booleanValue;
1399 }
1400 
1401 
1402 bool
1404 {
1405  return type_ == realValue;
1406 }
1407 
1408 
1409 bool
1411 {
1412  return isIntegral() || isDouble();
1413 }
1414 
1415 
1416 bool
1418 {
1419  return type_ == stringValue;
1420 }
1421 
1422 
1423 bool
1425 {
1426  return type_ == nullValue || type_ == arrayValue;
1427 }
1428 
1429 
1430 bool
1432 {
1433  return type_ == nullValue || type_ == objectValue;
1434 }
1435 
1436 
1437 void
1438 Value::setComment( const char *comment,
1439  CommentPlacement placement )
1440 {
1441  if ( !comments_ )
1442  comments_ = new CommentInfo[numberOfCommentPlacement];
1443  comments_[placement].setComment( comment );
1444 }
1445 
1446 
1447 void
1448 Value::setComment( const std::string &comment,
1449  CommentPlacement placement )
1450 {
1451  setComment( comment.c_str(), placement );
1452 }
1453 
1454 
1455 bool
1457 {
1458  return comments_ != 0 && comments_[placement].comment_ != 0;
1459 }
1460 
1461 std::string
1463 {
1464  if ( hasComment(placement) )
1465  return comments_[placement].comment_;
1466  return "";
1467 }
1468 
1469 
1470 std::string
1472 {
1473  StyledWriter writer;
1474  return writer.write( *this );
1475 }
1476 
1477 
1480 {
1481  switch ( type_ )
1482  {
1483 #ifdef JSON_VALUE_USE_INTERNAL_MAP
1484  case arrayValue:
1485  if ( value_.array_ )
1486  {
1487  ValueInternalArray::IteratorState it;
1488  value_.array_->makeBeginIterator( it );
1489  return const_iterator( it );
1490  }
1491  break;
1492  case objectValue:
1493  if ( value_.map_ )
1494  {
1495  ValueInternalMap::IteratorState it;
1496  value_.map_->makeBeginIterator( it );
1497  return const_iterator( it );
1498  }
1499  break;
1500 #else
1501  case arrayValue:
1502  case objectValue:
1503  if ( value_.map_ )
1504  return const_iterator( value_.map_->begin() );
1505  break;
1506 #endif
1507  default:
1508  break;
1509  }
1510  return const_iterator();
1511 }
1512 
1514 Value::end() const
1515 {
1516  switch ( type_ )
1517  {
1518 #ifdef JSON_VALUE_USE_INTERNAL_MAP
1519  case arrayValue:
1520  if ( value_.array_ )
1521  {
1522  ValueInternalArray::IteratorState it;
1523  value_.array_->makeEndIterator( it );
1524  return const_iterator( it );
1525  }
1526  break;
1527  case objectValue:
1528  if ( value_.map_ )
1529  {
1530  ValueInternalMap::IteratorState it;
1531  value_.map_->makeEndIterator( it );
1532  return const_iterator( it );
1533  }
1534  break;
1535 #else
1536  case arrayValue:
1537  case objectValue:
1538  if ( value_.map_ )
1539  return const_iterator( value_.map_->end() );
1540  break;
1541 #endif
1542  default:
1543  break;
1544  }
1545  return const_iterator();
1546 }
1547 
1548 
1551 {
1552  switch ( type_ )
1553  {
1554 #ifdef JSON_VALUE_USE_INTERNAL_MAP
1555  case arrayValue:
1556  if ( value_.array_ )
1557  {
1558  ValueInternalArray::IteratorState it;
1559  value_.array_->makeBeginIterator( it );
1560  return iterator( it );
1561  }
1562  break;
1563  case objectValue:
1564  if ( value_.map_ )
1565  {
1566  ValueInternalMap::IteratorState it;
1567  value_.map_->makeBeginIterator( it );
1568  return iterator( it );
1569  }
1570  break;
1571 #else
1572  case arrayValue:
1573  case objectValue:
1574  if ( value_.map_ )
1575  return iterator( value_.map_->begin() );
1576  break;
1577 #endif
1578  default:
1579  break;
1580  }
1581  return iterator();
1582 }
1583 
1586 {
1587  switch ( type_ )
1588  {
1589 #ifdef JSON_VALUE_USE_INTERNAL_MAP
1590  case arrayValue:
1591  if ( value_.array_ )
1592  {
1593  ValueInternalArray::IteratorState it;
1594  value_.array_->makeEndIterator( it );
1595  return iterator( it );
1596  }
1597  break;
1598  case objectValue:
1599  if ( value_.map_ )
1600  {
1601  ValueInternalMap::IteratorState it;
1602  value_.map_->makeEndIterator( it );
1603  return iterator( it );
1604  }
1605  break;
1606 #else
1607  case arrayValue:
1608  case objectValue:
1609  if ( value_.map_ )
1610  return iterator( value_.map_->end() );
1611  break;
1612 #endif
1613  default:
1614  break;
1615  }
1616  return iterator();
1617 }
1618 
1619 
1620 // class PathArgument
1621 // //////////////////////////////////////////////////////////////////
1622 
1624  : kind_( kindNone )
1625 {
1626 }
1627 
1628 
1630  : index_( index )
1631  , kind_( kindIndex )
1632 {
1633 }
1634 
1635 
1636 PathArgument::PathArgument( const char *key )
1637  : key_( key )
1638  , kind_( kindKey )
1639 {
1640 }
1641 
1642 
1643 PathArgument::PathArgument( const std::string &key )
1644  : key_( key.c_str() )
1645  , kind_( kindKey )
1646 {
1647 }
1648 
1649 // class Path
1650 // //////////////////////////////////////////////////////////////////
1651 
1652 Path::Path( const std::string &path,
1653  const PathArgument &a1,
1654  const PathArgument &a2,
1655  const PathArgument &a3,
1656  const PathArgument &a4,
1657  const PathArgument &a5 )
1658 {
1659  InArgs in;
1660  in.push_back( &a1 );
1661  in.push_back( &a2 );
1662  in.push_back( &a3 );
1663  in.push_back( &a4 );
1664  in.push_back( &a5 );
1665  makePath( path, in );
1666 }
1667 
1668 
1669 void
1670 Path::makePath( const std::string &path,
1671  const InArgs &in )
1672 {
1673  const char *current = path.c_str();
1674  const char *end = current + path.length();
1675  InArgs::const_iterator itInArg = in.begin();
1676  while ( current != end )
1677  {
1678  if ( *current == '[' )
1679  {
1680  ++current;
1681  if ( *current == '%' )
1682  addPathInArg( path, in, itInArg, PathArgument::kindIndex );
1683  else
1684  {
1685  ArrayIndex index = 0;
1686  for ( ; current != end && *current >= '0' && *current <= '9'; ++current )
1687  index = index * 10 + ArrayIndex(*current - '0');
1688  args_.push_back( index );
1689  }
1690  if ( current == end || *current++ != ']' )
1691  invalidPath( path, int(current - path.c_str()) );
1692  }
1693  else if ( *current == '%' )
1694  {
1695  addPathInArg( path, in, itInArg, PathArgument::kindKey );
1696  ++current;
1697  }
1698  else if ( *current == '.' )
1699  {
1700  ++current;
1701  }
1702  else
1703  {
1704  const char *beginName = current;
1705  while ( current != end && !strchr( "[.", *current ) )
1706  ++current;
1707  args_.push_back( std::string( beginName, current ) );
1708  }
1709  }
1710 }
1711 
1712 
1713 void
1714 Path::addPathInArg( const std::string &path,
1715  const InArgs &in,
1716  InArgs::const_iterator &itInArg,
1717  PathArgument::Kind kind )
1718 {
1719  if ( itInArg == in.end() )
1720  {
1721  // Error: missing argument %d
1722  }
1723  else if ( (*itInArg)->kind_ != kind )
1724  {
1725  // Error: bad argument type
1726  }
1727  else
1728  {
1729  args_.push_back( **itInArg );
1730  }
1731 }
1732 
1733 
1734 void
1735 Path::invalidPath( const std::string &path,
1736  int location )
1737 {
1738  // Error: invalid path.
1739 }
1740 
1741 
1742 const Value &
1743 Path::resolve( const Value &root ) const
1744 {
1745  const Value *node = &root;
1746  for ( Args::const_iterator it = args_.begin(); it != args_.end(); ++it )
1747  {
1748  const PathArgument &arg = *it;
1749  if ( arg.kind_ == PathArgument::kindIndex )
1750  {
1751  if ( !node->isArray() || node->isValidIndex( arg.index_ ) )
1752  {
1753  // Error: unable to resolve path (array value expected at position...
1754  }
1755  node = &((*node)[arg.index_]);
1756  }
1757  else if ( arg.kind_ == PathArgument::kindKey )
1758  {
1759  if ( !node->isObject() )
1760  {
1761  // Error: unable to resolve path (object value expected at position...)
1762  }
1763  node = &((*node)[arg.key_]);
1764  if ( node == &Value::null )
1765  {
1766  // Error: unable to resolve path (object has no member named '' at position...)
1767  }
1768  }
1769  }
1770  return *node;
1771 }
1772 
1773 
1774 Value
1775 Path::resolve( const Value &root,
1776  const Value &defaultValue ) const
1777 {
1778  const Value *node = &root;
1779  for ( Args::const_iterator it = args_.begin(); it != args_.end(); ++it )
1780  {
1781  const PathArgument &arg = *it;
1782  if ( arg.kind_ == PathArgument::kindIndex )
1783  {
1784  if ( !node->isArray() || node->isValidIndex( arg.index_ ) )
1785  return defaultValue;
1786  node = &((*node)[arg.index_]);
1787  }
1788  else if ( arg.kind_ == PathArgument::kindKey )
1789  {
1790  if ( !node->isObject() )
1791  return defaultValue;
1792  node = &((*node)[arg.key_]);
1793  if ( node == &Value::null )
1794  return defaultValue;
1795  }
1796  }
1797  return *node;
1798 }
1799 
1800 
1801 Value &
1802 Path::make( Value &root ) const
1803 {
1804  Value *node = &root;
1805  for ( Args::const_iterator it = args_.begin(); it != args_.end(); ++it )
1806  {
1807  const PathArgument &arg = *it;
1808  if ( arg.kind_ == PathArgument::kindIndex )
1809  {
1810  if ( !node->isArray() )
1811  {
1812  // Error: node is not an array at position ...
1813  }
1814  node = &((*node)[arg.index_]);
1815  }
1816  else if ( arg.kind_ == PathArgument::kindKey )
1817  {
1818  if ( !node->isObject() )
1819  {
1820  // Error: node is not an object at position...
1821  }
1822  node = &((*node)[arg.key_]);
1823  }
1824  }
1825  return *node;
1826 }
1827 
1828 
1829 } // namespace Json
bool hasComment(CommentPlacement placement) const
Path(const std::string &path, const PathArgument &a1=PathArgument(), const PathArgument &a2=PathArgument(), const PathArgument &a3=PathArgument(), const PathArgument &a4=PathArgument(), const PathArgument &a5=PathArgument())
Int64 LargestInt
Definition: config.h:89
UInt64 asUInt64() const
Definition: json_value.cpp:779
Writes a Value in JSON format in a human friendly way.
Definition: writer.h:72
Value & make(Value &root) const
Creates the "path" to access the specified node and returns a reference on the node.
Int asInt() const
Definition: json_value.cpp:690
std::string asString() const
Definition: json_value.cpp:658
static const Int64 maxInt64
Maximum signed 64 bits int value that can be stored in a Json::Value.
Definition: value.h:157
unsigned int ArrayIndex
Definition: forwards.h:23
bool isNull() const
std::vector< std::string > Members
Definition: value.h:126
double asDouble() const
Definition: json_value.cpp:830
array value (ordered list)
Definition: value.h:38
static char * duplicateStringValue(const char *value, unsigned int length=unknown)
Duplicates the specified string value.
Definition: json_value.cpp:54
unsigned __int64 UInt64
Definition: config.h:84
LargestUInt asLargestUInt() const
Definition: json_value.cpp:819
unsigned integer value
Definition: value.h:34
bool isBool() const
bool operator<(const Value &other) const
Definition: json_value.cpp:538
Json::ArrayIndex ArrayIndex
Definition: value.h:137
int compare(const Value &other) const
Definition: json_value.cpp:527
object value (collection of name/value pairs).
Definition: value.h:39
static const Int maxInt
Maximum signed int value that can be stored in a Json::Value.
Definition: value.h:150
bool empty() const
Return true if empty array, empty object, or null; otherwise, false.
Lightweight wrapper to tag static string.
Definition: value.h:69
Value removeMember(const char *key)
Remove and return the named member.
static const UInt maxUInt
Maximum unsigned int value that can be stored in a Json::Value.
Definition: value.h:152
static ValueArrayAllocator *& arrayAllocator()
virtual ValueInternalMap * newMap()=0
const iterator for object and array value.
Definition: value.h:983
bool asBool() const
Definition: json_value.cpp:888
virtual void destructArray(ValueInternalArray *array)=0
bool isObject() const
Value(ValueType type=nullValue)
Create a default Value of the given type.
Definition: json_value.cpp:236
Experimental and untested: represents an element of the "path" to access a node.
Definition: value.h:504
void setComment(const char *comment, CommentPlacement placement)
Comments must be //... or /* ... */.
bool isDouble() const
std::string getComment(CommentPlacement placement) const
Include delimiters and embedded newlines.
static const LargestInt minLargestInt
Minimum signed integer value that can be stored in a Json::Value.
Definition: value.h:141
'null' value
Definition: value.h:32
CommentPlacement
Definition: value.h:42
virtual ValueInternalArray * newArray()=0
bool isMember(const char *key) const
Return true if the object has a member named key.
#define JSON_ASSERT_MESSAGE(condition, message)
Definition: json_value.cpp:26
virtual ValueInternalArray * newArrayCopy(const ValueInternalArray &other)=0
UInt64 LargestUInt
Definition: config.h:90
Value & operator[](ArrayIndex index)
Access an array element (zero based index ).
static const Value null
Definition: value.h:139
bool isIntegral() const
ValueConstIterator const_iterator
Definition: value.h:128
static bool in(Reader::Char c, Reader::Char c1, Reader::Char c2, Reader::Char c3, Reader::Char c4)
Definition: json_reader.cpp:55
virtual std::string write(const Value &root)
Serialize a Value in JSON format.
UInt asUInt() const
Definition: json_value.cpp:719
JSON (JavaScript Object Notation).
Definition: config.h:73
Members getMemberNames() const
Return a list of the member names.
Json::Int64 Int64
Definition: value.h:133
bool isString() const
void swap(Value &other)
Swap values.
Definition: json_value.cpp:508
const char * c_str() const
Definition: value.h:82
const char * asCString() const
Definition: json_value.cpp:650
static const UInt64 maxUInt64
Maximum unsigned 64 bits int value that can be stored in a Json::Value.
Definition: value.h:159
bool isInt() const
static const unsigned int unknown
Unknown size marker.
Definition: json_value.cpp:43
double value
Definition: value.h:35
bool operator>(const Value &other) const
Definition: json_value.cpp:594
static ValueMapAllocator *& mapAllocator()
bool operator>=(const Value &other) const
Definition: json_value.cpp:588
Json::UInt UInt
Definition: value.h:129
bool operator==(const Value &other) const
Definition: json_value.cpp:600
const Value & resolve(const Value &root) const
bool isValidIndex(ArrayIndex index) const
Return true if index < size().
Value & append(const Value &value)
Append value to array at the end.
Value & operator=(const Value &other)
Definition: json_value.cpp:500
float asFloat() const
Definition: json_value.cpp:859
ArrayIndex size() const
Number of values in array or object.
Definition: json_value.cpp:966
std::string toStyledString() const
Json::UInt64 UInt64
Definition: value.h:132
Json::Int Int
Definition: value.h:130
bool isUInt() const
#define JSON_ASSERT_UNREACHABLE
Definition: json_value.cpp:23
Represents a JSON value.
Definition: value.h:118
Int64 asInt64() const
Definition: json_value.cpp:751
#define JSON_ASSERT(condition)
Definition: json_value.cpp:24
ValueType type() const
Definition: json_value.cpp:520
ValueIterator iterator
Definition: value.h:127
bool isConvertibleTo(ValueType other) const
Definition: json_value.cpp:914
static const Int64 minInt64
Minimum signed 64 bits int value that can be stored in a Json::Value.
Definition: value.h:155
static const Int minInt
Minimum signed int value that can be stored in a Json::Value.
Definition: value.h:148
bool operator!() const
Return isNull()
LargestInt asLargestInt() const
Definition: json_value.cpp:808
unsigned int UInt
Definition: config.h:75
virtual ValueInternalMap * newMapCopy(const ValueInternalMap &other)=0
void resize(ArrayIndex size)
Resize the array to size elements.
void clear()
Remove all object members and array elements.
Iterator for object and array value.
Definition: value.h:1041
bool operator<=(const Value &other) const
Definition: json_value.cpp:582
__int64 Int64
Definition: config.h:83
virtual void destructMap(ValueInternalMap *map)=0
static void releaseStringValue(char *value)
Free the string duplicated by duplicateStringValue().
Definition: json_value.cpp:70
ValueType
Type of the value held by a Value object.
Definition: value.h:30
Value get(ArrayIndex index, const Value &defaultValue) const
If the array contains at least index+1 elements, returns the element value, otherwise returns default...
bool isArray() const
bool value
Definition: value.h:37
signed integer value
Definition: value.h:33
#define JSON_FAIL_MESSAGE(message)
Definition: json_value.cpp:25
int Int
Definition: config.h:74
UTF-8 string value.
Definition: value.h:36
const_iterator begin() const
bool isNumeric() const
bool operator!=(const Value &other) const
Definition: json_value.cpp:644
static const LargestInt maxLargestInt
Maximum signed integer value that can be stored in a Json::Value.
Definition: value.h:143
const_iterator end() const
static const LargestUInt maxLargestUInt
Maximum unsigned integer value that can be stored in a Json::Value.
Definition: value.h:145

SourceForge Logo hosts this site. Send comments to:
Json-cpp Developers