source: chevmsgr/trunk/json.h@ 4

Last change on this file since 4 was 4, checked in by cheese, 9 years ago

자 이제 시작이야 (졸작을)

File size: 25.7 KB
Line 
1/*
2 SuperEasyJSON
3 http://www.sourceforge.net/p/supereasyjson
4
5 The MIT License (MIT)
6
7 Copyright (c) 2013 Jeff Weinstein (jeff.weinstein at gmail)
8
9 Permission is hereby granted, free of charge, to any person obtaining a copy
10 of this software and associated documentation files (the "Software"), to deal
11 in the Software without restriction, including without limitation the rights
12 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
13 copies of the Software, and to permit persons to whom the Software is
14 furnished to do so, subject to the following conditions:
15
16 The above copyright notice and this permission notice shall be included in
17 all copies or substantial portions of the Software.
18
19 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
20 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
22 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
23 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
24 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
25 THE SOFTWARE.
26
27 CHANGELOG:
28 ==========
29
30 8/31/2014:
31 ---------
32 * Fixed bug from last update that broke false/true boolean usage. Courtesy of Vasi B.
33 * Change postfix increment of iterators in Serialize to prefix, courtesy of Vasi B.
34 * More improvements to validity checking of non string/object/array types. Should
35 catch even more invalid usage types such as -1jE5, falsee, trueeeeeee
36 {"key" : potato} (that should be {"key" : "potato"}), etc.
37 * Switched to strtol and strtod from atof/atoi in Serialize for better error handling.
38 * Fix for GCC order of initialization warnings, courtsey of Vasi B.
39
40 8/17/2014:
41 ----------
42 * Better error handling (and bug fixing) for invalid JSON. Previously, something such as:
43 {"def": j[{"a": 100}],"abc": 123}
44 would result in at best, a crash, and at worst, nothing when this was passed to
45 the Deserialize method. Note that the "j" is invalid in this example. This led
46 to further fixes for other invalid syntax:
47 - Use of multiple 'e', for example: 1ee4 is not valid
48 - Use of '.' when not preceded by a digit is invalid. For example: .1 is
49 incorrect, but 0.1 is fine.
50 - Using 'e' when not preceded by a digit. For example, e4 isn't valid but 1e4 is.
51
52 The deserialize method should properly handle these problems and when there's an
53 error, it returns a Value object with the NULLVal type. Check this type to see
54 if there's an error.
55
56 Issue reported by Imre Pechan.
57
58 7/21/2014:
59 ----------
60 * All asserts removed and replaced with exceptions, as per request from many users.
61 Instead of asserting, functions will throw a std::runtime_error with
62 appropriate error message.
63 * Added versions of the Value::To* functions that take a default parameter.
64 In the event of an error (like calling Value::ToInt() when it's type is an Object),
65 the default value you specified will be returned. Courtesy of PeterSvP
66 * Fixed type mismatch warning, courtesy of Per Rovegård
67 * Initialized some variables in the various Value constructors to defaults for
68 better support with full blast g++ warnings, courtesy of Mark Odell.
69 * Changed Value::ToString to return a const std::string& instead of std::string
70 to avoid unnecessary copying.
71 * Improved some commenting
72 * Fixed a bug where a capital E for scientific notation numbers wasn't
73 recognized, only lowercase e.
74 * VASTLY OVERHAULED AND IMPROVED THE README FILE, PLEASE CONSULT IT FOR
75 IN DEPTH USAGE AND EXAMPLES.
76
77
78 2/8/2014:
79 ---------
80 MAJOR BUG FIXES, all courtesy of Per Rovegård, Ph.D.
81 * Feature request: HasKey and HasKeys added to Value for convenience and
82 to avoid having to make a temporary object.
83 * Strings should now be properly unescaped. Previously, as an example, the
84 string "\/Date(1390431949211+0100)\/\" would be parsed as
85 \/Date(1390431949211+0100)\/. The string is now properly parsed as
86 /Date(1390431949211+0100)/.
87 As per http://www.json.org the other escape characters including
88 \u+4 hex digits will now be properly unescaped. So for example,
89 \u0061 now becomes "A".
90 * Serialize now supports serializing a toplevel array (which is valid JSON).
91 The parameter it takes is now a Value, but existing code doesn't
92 need to be changed.
93 * Fixed bug with checking for proper opening/closing sequence for braces/brackets.
94 Previously, this code:
95 const char *json = "{\"arr\":[{}}]}";
96 auto val = json::Deserialize(json);
97 worked fine with no errors. That's a bug. I did a major overhaul so that
98 now improperly formatted pairs will now correctly result in an error.
99 * Made internal deserialize methods static
100
101 1/30/2014:
102 ----------
103 * Changed #pragma once to the standard #ifndef header guard style for
104 better compatibility.
105 * Added a [] operator for Value that takes a const char* as an argument
106 to avoid having to explicitly (and annoyingly) cast to std::string.
107 Thus, my_value["asdf"] = "a string" should now work fine.
108 The same has been added to the Object class.
109 * Added non-operator methods of casting a Value to int/string/bool/etc.
110 Implicitly casting a Value to a std::string doesn't work as per C++
111 rules. As such, previously to assign a Value to a std::string you
112 had to do:
113 my_std_string = (std::string)my_value;
114 You can now instead do:
115 my_std_string = my_value.ToString();
116 If you want more information on why this can't be done, please read
117 this topic for more details:
118 http://stackoverflow.com/questions/3518145/c-overloading-conversion-operator-for-custom-type-to-stdstring
119
120 1/27/2014
121 ----------
122 * Deserialize will now return a NULLVal Value instance if there was an
123 error instead of asserting. This way you can handle however you want to
124 invalid JSON being passed in. As a top level object must be either an
125 array or an object, a NULL value return indicates an invalid result.
126
127 1/11/2014
128 ---------
129 * Major bug fix: Strings containing []{} characters could cause
130 parsing errors under certain conditions. I've just tested
131 the class parsing a 300KB JSON file with all manner of bizarre
132 characters and permutations and it worked, so hopefully this should
133 be the end of "major bug" fixes.
134
135 1/10/2014
136 ---------
137 Bug fixes courtesy of Gerry Beauregard:
138 * Pretty big bug: was using wrong string paramter in ::Deserialize
139 and furthermore it wasn't being trimmed.
140 * Object::HasKeys now casts the return value to avoid compiler warnings.
141 * Slight optimization to the Trim function
142 * Made asserts in ::Deserialize easier to read
143
144 1/9/2014
145 --------
146 * Major bug fix: for JSON strings containing \" (as in, two characters,
147 not the escaped " character), the lib would mess up and not parse
148 correctly.
149 * Major bug fix: I erroneously was assuming that all root JSON types
150 had to be an object. This was an oversight, as a root JSON
151 object can be an array. I have therefore changed the Deserialize
152 method to return a json::Value rather than a json::Object. This
153 will NOT impact any existing code you have, as a json::Value will
154 cast to a json::Object (if it is indeed an object). But for
155 correctness, you should be using json::Value = Deserialize...
156 The Value type can be checked if it's an array (or any other type),
157 and furthermore can even be accessed with the [] operator for
158 convenience.
159 * I've made the NULL value type set numeric fields to 0 and bool to false.
160 This is for convenience for using the NULL type as a default return
161 value in your code.
162 * asserts added to casting (Gerry Beauregard)
163 * Added method HasKeys to json::Object which will check if all the keys
164 specified are in the object, returning the index of the first key
165 not found or -1 if all found (hoppe).
166
167 1/4/2014
168 --------
169 * Fixed bug where booleans were being parsed as doubles (Gerry Beauregard).
170
171 1/2/2014 v3
172 ------------
173 * More missing headers added for VisualStudio 2012
174 * Switched to snprintf instead of sprintf (or sprintf_s in MSVC)
175
176 1/2/2014 v2
177 -----------
178 * Added yet more missing headers for compiling on GNU and Linux systems
179 * Made Deserialize copy the passed in string so it won't mangle it
180
181 1/2/2014
182 --------
183 * Fixed previous changelog years. Got ahead of myself and marked them
184 as 2014 when they were in fact done in 2013.
185 * Added const version of [] to Array/Object/Value
186 * Removed C++11 requirements, should work with older compilers
187 (thanks to Meng Wang for pointing that out)
188 * Made ValueMap and ValueVector typedefs in Object/Value public
189 so you can actually iterate over the class
190 * Added HasKey and HasValue to Object/Array for convenience
191 (note this could have been done comparing .find to .end)
192
193 12/29/2013 v2
194 -------------
195 * Added .size() field to Value. Returns 1 for non Array/Object types,
196 otherwise the number of elements contained.
197 * Added .find() to Object to search for a key. Returns Object::end()
198 if not found, otherwise the Value.
199 Example: bool found = my_obj.find("some key") != my_obj.end();
200 * Added .find() to Array to search for a value. Just a convenience
201 wrapper for std::find(Array::begin(), Array::end(), Value)
202 * Added ==, !=, <, >, <=, >= operators to Object/Array/Value.
203 For Objects/Arrays, the operators function just like they do for a
204 std::map and std::vector, respectively.
205 * Added IsNumeric to Value to indicate if it's an int/float/double type.
206
207 12/29/2013
208 ----------
209 * Added the DoubleVal type which stores, you guessed it, double values.
210 * Bug fix for floats with an exact integer value. Now, setting any numerical
211 field will also set the fields for the other numerical types. So if you
212 have obj["value"] = 12, then the int/float/double cast methods will
213 return 12/12.0f/12.0. Previously, in the example above, only the int
214 value was set, making a cast to float return 0.
215 * Bug fix for deserializing JSON strings that contained large integer values.
216 Now if the numerical value of a key in a JSON string contains a number
217 less than INT_MIN or greater than INT_MAX it will be stored as a double.
218 Note that as mentioned above, all numerical fields are set.
219 * Should work fine with scientific notation values now.
220
221 12/28/2013
222 ----------
223
224 * Fixed a bug where if there were spaces around values or key names in a JSON
225 string passed in to Deserialize, invalid results or asserts would occur.
226 (Fix courtesy of Gerry Beauregard)
227
228 * Added method named "Clear()" to Object/Array/Value to reset state
229
230 * Added license to header file for easyness (totally valid word).
231 */
232
233#ifndef __SUPER_EASY_JSON_H__
234#define __SUPER_EASY_JSON_H__
235
236#include <vector>
237#include <map>
238#include <string>
239#include <stdexcept>
240
241
242// PLEASE SEE THE README FOR USAGE INFORMATION AND EXAMPLES. Comments will be kept to a minimum to reduce clutter.
243namespace json
244{
245 enum ValueType
246 {
247 NULLVal,
248 StringVal,
249 IntVal,
250 FloatVal,
251 DoubleVal,
252 ObjectVal,
253 ArrayVal,
254 BoolVal
255 };
256
257 class Value;
258
259 // Represents a JSON object which is of the form {string:value, string:value, ...} Where string is the "key" name and is
260 // of the form "" or "characters". Value is either of: string, number, object, array, boolean, null
261 class Object
262 {
263 public:
264
265 // This is the type used to store key/value pairs. If you want to get an iterator for this class to iterate over its members,
266 // use this.
267 // For example: Object::ValueMap::iterator my_iterator;
268 typedef std::map<std::string, Value> ValueMap;
269
270 protected:
271
272 ValueMap mValues;
273
274 public:
275
276 Object();
277 Object(const Object& obj);
278
279 Object& operator =(const Object& obj);
280
281 friend bool operator ==(const Object& lhs, const Object& rhs);
282 inline friend bool operator !=(const Object& lhs, const Object& rhs) {return !(lhs == rhs);}
283 friend bool operator <(const Object& lhs, const Object& rhs);
284 inline friend bool operator >(const Object& lhs, const Object& rhs) {return operator<(rhs, lhs);}
285 inline friend bool operator <=(const Object& lhs, const Object& rhs) {return !operator>(lhs, rhs);}
286 inline friend bool operator >=(const Object& lhs, const Object& rhs) {return !operator<(lhs, rhs);}
287
288 // Just like a std::map, you can get the value for a key by using the index operator. You could also
289 // use this to insert a value if it doesn't exist, or overwrite it if it does. Example:
290 // Value my_val = my_object["some key name"];
291 // my_object["some key name"] = "overwriting the value with this new string value";
292 // my_object["new key name"] = "a new key being inserted";
293 Value& operator [](const std::string& key);
294 const Value& operator [](const std::string& key) const;
295 Value& operator [](const char* key);
296 const Value& operator [](const char* key) const;
297
298 ValueMap::const_iterator begin() const;
299 ValueMap::const_iterator end() const;
300 ValueMap::iterator begin();
301 ValueMap::iterator end();
302
303 // Find will return end() if the key can't be found, just like std::map does. ->first will be the key (a std::string),
304 // ->second will be the Value.
305 ValueMap::iterator find(const std::string& key);
306 ValueMap::const_iterator find(const std::string& key) const;
307
308 // Convenience wrapper to search for a key
309 bool HasKey(const std::string& key) const;
310
311 // Checks if the object contains all the keys in the array. If it does, returns -1.
312 // If it doesn't, returns the index of the first key it couldn't find.
313 int HasKeys(const std::vector<std::string>& keys) const;
314 int HasKeys(const char* keys[], int key_count) const;
315
316 // Removes all values and resets the state back to default
317 void Clear();
318
319 size_t size() const {return mValues.size();}
320
321 };
322
323 // Represents a JSON Array which is of the form [value, value, ...] where value is either of: string, number, object, array, boolean, null
324 class Array
325 {
326 public:
327
328 // This is the type used to store values. If you want to get an iterator for this class to iterate over its members,
329 // use this.
330 // For example: Array::ValueVector::iterator my_array_iterator;
331 typedef std::vector<Value> ValueVector;
332
333 protected:
334
335 ValueVector mValues;
336
337 public:
338
339 Array();
340 Array(const Array& a);
341
342 Array& operator =(const Array& a);
343
344 friend bool operator ==(const Array& lhs, const Array& rhs);
345 inline friend bool operator !=(const Array& lhs, const Array& rhs) {return !(lhs == rhs);}
346 friend bool operator <(const Array& lhs, const Array& rhs);
347 inline friend bool operator >(const Array& lhs, const Array& rhs) {return operator<(rhs, lhs);}
348 inline friend bool operator <=(const Array& lhs, const Array& rhs) {return !operator>(lhs, rhs);}
349 inline friend bool operator >=(const Array& lhs, const Array& rhs) {return !operator<(lhs, rhs);}
350
351 Value& operator[] (size_t i);
352 const Value& operator[] (size_t i) const;
353
354 ValueVector::const_iterator begin() const;
355 ValueVector::const_iterator end() const;
356 ValueVector::iterator begin();
357 ValueVector::iterator end();
358
359 // Just a convenience wrapper for doing a std::find(Array::begin(), Array::end(), Value)
360 ValueVector::iterator find(const Value& v);
361 ValueVector::const_iterator find(const Value& v) const;
362
363 // Convenience wrapper to check if a value is in the array
364 bool HasValue(const Value& v) const;
365
366 // Removes all values and resets the state back to default
367 void Clear();
368
369 void push_back(const Value& v);
370 void insert(size_t index, const Value& v);
371 size_t size() const;
372 };
373
374 // Represents a JSON value which is either of: string, number, object, array, boolean, null
375 class Value
376 {
377 protected:
378
379 ValueType mValueType;
380 int mIntVal;
381 float mFloatVal;
382 double mDoubleVal;
383 std::string mStringVal;
384 Object mObjectVal;
385 Array mArrayVal;
386 bool mBoolVal;
387
388 public:
389
390 Value() : mValueType(NULLVal), mIntVal(0), mFloatVal(0), mDoubleVal(0), mBoolVal(false) {}
391 Value(int v) : mValueType(IntVal), mIntVal(v), mFloatVal((float)v), mDoubleVal((double)v), mBoolVal(false) {}
392 Value(float v) : mValueType(FloatVal), mIntVal((int)v), mFloatVal(v), mDoubleVal((double)v), mBoolVal(false) {}
393 Value(double v) : mValueType(DoubleVal), mIntVal((int)v), mFloatVal((float)v), mDoubleVal(v), mBoolVal(false) {}
394 Value(const std::string& v) : mValueType(StringVal), mIntVal(), mFloatVal(), mDoubleVal(), mStringVal(v), mBoolVal(false) {}
395 Value(const char* v) : mValueType(StringVal), mIntVal(), mFloatVal(), mDoubleVal(), mStringVal(v), mBoolVal(false) {}
396 Value(const Object& v) : mValueType(ObjectVal), mIntVal(), mFloatVal(), mDoubleVal(), mObjectVal(v), mBoolVal(false) {}
397 Value(const Array& v) : mValueType(ArrayVal), mIntVal(), mFloatVal(), mDoubleVal(), mArrayVal(v), mBoolVal(false) {}
398 Value(bool v) : mValueType(BoolVal), mIntVal(), mFloatVal(), mDoubleVal(), mBoolVal(v) {}
399 Value(const Value& v);
400
401 // Use this to determine the underlying type that this Value class represents. It will be one of the
402 // ValueType enums as defined at the top of this file.
403 ValueType GetType() const {return mValueType;}
404
405 // Convenience method that checks if this type is an int/double/float
406 bool IsNumeric() const {return (mValueType == IntVal) || (mValueType == DoubleVal) || (mValueType == FloatVal);}
407
408 Value& operator =(const Value& v);
409
410 friend bool operator ==(const Value& lhs, const Value& rhs);
411 inline friend bool operator !=(const Value& lhs, const Value& rhs) {return !(lhs == rhs);}
412 friend bool operator <(const Value& lhs, const Value& rhs);
413 inline friend bool operator >(const Value& lhs, const Value& rhs) {return operator<(rhs, lhs);}
414 inline friend bool operator <=(const Value& lhs, const Value& rhs) {return !operator>(lhs, rhs);}
415 inline friend bool operator >=(const Value& lhs, const Value& rhs) {return !operator<(lhs, rhs);}
416
417
418 // If this value represents an object or array, you can use the [] indexing operator
419 // just like you would with the native json::Array or json::Object classes.
420 // THROWS A std::runtime_error IF NOT AN ARRAY OR OBJECT.
421 Value& operator [](size_t idx);
422 const Value& operator [](size_t idx) const;
423 Value& operator [](const std::string& key);
424 const Value& operator [](const std::string& key) const;
425 Value& operator [](const char* key);
426 const Value& operator [](const char* key) const;
427
428 // If this value represents an object, these methods let you check if a single key or an array of
429 // keys is contained within it.
430 // THROWS A std::runtime_error IF NOT AN OBJECT.
431 bool HasKey(const std::string& key) const;
432 int HasKeys(const std::vector<std::string>& keys) const;
433 int HasKeys(const char* keys[], int key_count) const;
434
435
436 // non-operator versions, **will throw a std::runtime_error if invalid with an appropriate error message**
437 int ToInt() const;
438 float ToFloat() const;
439 double ToDouble() const;
440 bool ToBool() const;
441 const std::string& ToString() const;
442 Object ToObject() const;
443 Array ToArray() const;
444
445 // These versions do the same as above but will return your specified default value in the event there's an error, and thus **don't** throw an exception.
446 int ToInt(int def) const {return IsNumeric() ? mIntVal : def;}
447 float ToFloat(float def) const {return IsNumeric() ? mFloatVal : def;}
448 double ToDouble(double def) const {return IsNumeric() ? mDoubleVal : def;}
449 bool ToBool(bool def) const {return (mValueType == BoolVal) ? mBoolVal : def;}
450 const std::string& ToString(const std::string& def) const {return (mValueType == StringVal) ? mStringVal : def;}
451
452
453 // Please note that as per C++ rules, implicitly casting a Value to a std::string won't work.
454 // This is because it could use the int/float/double/bool operators as well. So to assign a
455 // Value to a std::string you can either do:
456 // my_string = (std::string)my_value
457 // Or you can now do:
458 // my_string = my_value.ToString();
459 //
460 operator int() const;
461 operator float() const;
462 operator double() const;
463 operator bool() const;
464 operator std::string() const;
465 operator Object() const;
466 operator Array() const;
467
468 // Returns 1 for anything not an Array/ObjectVal
469 size_t size() const;
470
471 // Resets the state back to default, aka NULLVal
472 void Clear();
473
474 };
475
476 ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
477 ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
478 // Converts a JSON Object or Array instance into a JSON string representing it. RETURNS EMPTY STRING ON ERROR.
479 // As per JSON specification, a JSON data structure must be an array or an object. Thus, you must either pass in a
480 // json::Array, json::Object, or a json::Value that has an Array or Object as its underlying type.
481 std::string Serialize(const Value& obj);
482
483 // If there is an error, Value will be NULLVal. Pass in a valid JSON string (such as one returned from Serialize, or obtained
484 // elsewhere) to receive a Value in return that represents the JSON structure. Check the type of Value by calling GetType().
485 // It will be ObjectVal or ArrayVal (or NULLVal if invalid JSON). The Value class contains the operator [] for indexing in the
486 // case that the underlying type is an object or array. You may, if you prefer, create an object or array from the Value returned
487 // by this method by simply passing it into the constructor.
488 Value Deserialize(const std::string& str);
489
490 ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
491 ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
492 inline bool operator ==(const Object& lhs, const Object& rhs)
493 {
494 return lhs.mValues == rhs.mValues;
495 }
496
497 inline bool operator <(const Object& lhs, const Object& rhs)
498 {
499 return lhs.mValues < rhs.mValues;
500 }
501
502 inline bool operator ==(const Array& lhs, const Array& rhs)
503 {
504 return lhs.mValues == rhs.mValues;
505 }
506
507 inline bool operator <(const Array& lhs, const Array& rhs)
508 {
509 return lhs.mValues < rhs.mValues;
510 }
511
512 /* When comparing different numeric types, this method works the same as if you compared different numeric types
513 on your own. Thus it performs the same as if you, for example, did this:
514
515 int a = 1;
516 float b = 1.1f;
517 bool equivalent = a == b;
518
519 The same logic applies to the other comparison operators.
520 */
521 inline bool operator ==(const Value& lhs, const Value& rhs)
522 {
523 if ((lhs.mValueType != rhs.mValueType) && !lhs.IsNumeric() && !rhs.IsNumeric())
524 return false;
525
526 switch (lhs.mValueType)
527 {
528 case StringVal : return lhs.mStringVal == rhs.mStringVal;
529
530 case IntVal : if (rhs.GetType() == FloatVal)
531 return lhs.mIntVal == rhs.mFloatVal;
532 else if (rhs.GetType() == DoubleVal)
533 return lhs.mIntVal == rhs.mDoubleVal;
534 else if (rhs.GetType() == IntVal)
535 return lhs.mIntVal == rhs.mIntVal;
536 else
537 return false;
538
539 case FloatVal : if (rhs.GetType() == FloatVal)
540 return lhs.mFloatVal == rhs.mFloatVal;
541 else if (rhs.GetType() == DoubleVal)
542 return lhs.mFloatVal == rhs.mDoubleVal;
543 else if (rhs.GetType() == IntVal)
544 return lhs.mFloatVal == rhs.mIntVal;
545 else
546 return false;
547
548
549 case DoubleVal : if (rhs.GetType() == FloatVal)
550 return lhs.mDoubleVal == rhs.mFloatVal;
551 else if (rhs.GetType() == DoubleVal)
552 return lhs.mDoubleVal == rhs.mDoubleVal;
553 else if (rhs.GetType() == IntVal)
554 return lhs.mDoubleVal == rhs.mIntVal;
555 else
556 return false;
557
558 case BoolVal : return lhs.mBoolVal == rhs.mBoolVal;
559
560 case ObjectVal : return lhs.mObjectVal == rhs.mObjectVal;
561
562 case ArrayVal : return lhs.mArrayVal == rhs.mArrayVal;
563
564 default:
565 return true;
566 }
567 }
568
569 inline bool operator <(const Value& lhs, const Value& rhs)
570 {
571 if ((lhs.mValueType != rhs.mValueType) && !lhs.IsNumeric() && !rhs.IsNumeric())
572 return false;
573
574 switch (lhs.mValueType)
575 {
576 case StringVal : return lhs.mStringVal < rhs.mStringVal;
577
578 case IntVal : if (rhs.GetType() == FloatVal)
579 return lhs.mIntVal < rhs.mFloatVal;
580 else if (rhs.GetType() == DoubleVal)
581 return lhs.mIntVal < rhs.mDoubleVal;
582 else if (rhs.GetType() == IntVal)
583 return lhs.mIntVal < rhs.mIntVal;
584 else
585 return false;
586
587 case FloatVal : if (rhs.GetType() == FloatVal)
588 return lhs.mFloatVal < rhs.mFloatVal;
589 else if (rhs.GetType() == DoubleVal)
590 return lhs.mFloatVal < rhs.mDoubleVal;
591 else if (rhs.GetType() == IntVal)
592 return lhs.mFloatVal < rhs.mIntVal;
593 else
594 return false;
595
596 case DoubleVal : if (rhs.GetType() == FloatVal)
597 return lhs.mDoubleVal < rhs.mFloatVal;
598 else if (rhs.GetType() == DoubleVal)
599 return lhs.mDoubleVal < rhs.mDoubleVal;
600 else if (rhs.GetType() == IntVal)
601 return lhs.mDoubleVal < rhs.mIntVal;
602 else
603 return false;
604
605 case BoolVal : return lhs.mBoolVal < rhs.mBoolVal;
606
607 case ObjectVal : return lhs.mObjectVal < rhs.mObjectVal;
608
609 case ArrayVal : return lhs.mArrayVal < rhs.mArrayVal;
610
611 default:
612 return true;
613 }
614 }
615}
616
617#endif //__SUPER_EASY_JSON_H__
Note: See TracBrowser for help on using the repository browser.