0123
MbedJSONValue.cpp
- Committer:
- samux
- Date:
- 2011-09-22
- Revision:
- 3:f2ffae08b963
- Parent:
- 2:e39bfa3e917d
File content as of revision 3:f2ffae08b963:
#include "MbedJSONValue.h" # include <stdlib.h> # include <stdio.h> // Clean up void MbedJSONValue::clean() { switch (_type) { case TypeString: delete _value.asString; break; case TypeArray: for (int i = 0; i < index_array; i++) delete array[i]; index_array = 0; break; case TypeObject: for (int i = 0; i < index_token; i++) { delete token[i]; delete token_name[i]; } index_token = 0; break; default: break; } _type = TypeNull; _type = TypeNull; } bool MbedJSONValue::hasMember(char * name) { for(int i = 0; i < index_token; i++) if( !strcmp(name, (*(token_name[i])).c_str() )) return true; return false; } void copy(const std::string& s, std::back_insert_iterator<std::string> oi) { std::copy(s.begin(), s.end(), oi); } void serialize_str(const std::string& s, std::back_insert_iterator<std::string> oi) { *oi++ = '"'; for (std::string::const_iterator i = s.begin(); i != s.end(); ++i) { switch (*i) { #define MAP(val, sym) case val: copy(sym, oi); break MAP('"', "\\\""); MAP('\\', "\\\\"); MAP('/', "\\/"); MAP('\b', "\\b"); MAP('\f', "\\f"); MAP('\n', "\\n"); MAP('\r', "\\r"); MAP('\t', "\\t"); #undef MAP default: if ((unsigned char)*i < 0x20 || *i == 0x7f) { char buf[7]; sprintf(buf, "\\u%04x", *i & 0xff); copy(buf, buf + 6, oi); } else { *oi++ = *i; } break; } } *oi++ = '"'; } std::string MbedJSONValue::serialize(){ std::string s; serialize(std::back_inserter(s)); return s; } std::string MbedJSONValue::to_str(){ switch (_type) { case TypeNull: return "null"; case TypeBoolean: return _value.asBool ? "true" : "false"; case TypeInt: { char buf[10]; sprintf(buf, "%d", _value.asInt); return buf; } case TypeDouble: { char buf[10]; sprintf(buf, "%f", _value.asDouble); return buf; } default: break; } return NULL; } void MbedJSONValue::serialize(std::back_insert_iterator<std::string> oi) { switch (_type) { case TypeString: serialize_str(*_value.asString, oi); break; case TypeArray: { *oi++ = '['; for (int i = 0; i < index_array; i++) { if (i) *oi++ = ','; (*this)[i].serialize(oi); } *oi++ = ']'; break; } case TypeObject: { *oi++ = '{'; for (int i = 0; i < index_token; i++) { if (i) *oi++ = ','; serialize_str(*(token_name[i]), oi); *oi++ = ':'; (*(token[i])).serialize(oi); } *oi++ = '}'; break; } default: copy(to_str(), oi); break; } } MbedJSONValue& MbedJSONValue::operator[](int i) { _type = TypeArray; if (i < NB_TOKEN && index_array == i ) { #ifdef DEBUG printf("will add an element to the array\r\n"); #endif array[i] = new MbedJSONValue(); index_array++; return *(array[i]); } if (i < NB_TOKEN && index_array > i) return *(array[i]); //if the user is not doing something wrong, this code is never executed!! return *(new MbedJSONValue()); } MbedJSONValue& MbedJSONValue::operator[](std::string k) { _type = TypeObject; for (int i = 0; i < index_token; i++) { #ifdef DEBUG printf("k: %s\r\n", k.c_str()); printf("str: %s\r\n", token_name[i]->c_str()); #endif //existing token if (!strcmp(k.c_str(), token_name[i]->c_str())) { #ifdef DEBUG printf("token found: %d\r\n", i); #endif return *(token[i]); } } if(index_token >= NB_TOKEN) index_token = NB_TOKEN - 1; //non existing token token_name[index_token] = new std::string(k); token[index_token] = new MbedJSONValue(); index_token++; return *(token[index_token - 1]); } MbedJSONValue& MbedJSONValue::operator[](std::string k) const { for (int i = 0; i < index_token; i++) { #ifdef DEBUG printf("k: %s\r\n", k.c_str()); printf("str: %s\r\n", token_name[i]->c_str()); #endif if (!strcmp(k.c_str(), token_name[i]->c_str())) { #ifdef DEBUG printf("token found: %d\r\n", i); #endif return *(token[i]); } } //if the user is not doing something wrong, this code is never executed!! return *(new MbedJSONValue()); } // Operators MbedJSONValue& MbedJSONValue::operator=(MbedJSONValue const& rhs) { if (this != &rhs) { clean(); _type = rhs._type; switch (_type) { case TypeBoolean: _value.asBool = rhs._value.asBool; break; case TypeInt: _value.asInt = rhs._value.asInt; break; case TypeDouble: _value.asDouble = rhs._value.asDouble; break; case TypeString: _value.asString = new std::string(*rhs._value.asString); break; case TypeArray: for (int i = 0; i < rhs.index_array; i++) (*this)[i] = rhs[i]; case TypeObject: for (int i = 0; i < rhs.index_token; i++) (*this)[*(rhs.token_name[i])] = rhs[*(rhs.token_name[i])]; default: break; } } return *this; } // Works for strings, arrays, and structs. int MbedJSONValue::size() const { switch (_type) { case TypeString: return int(_value.asString->size()); case TypeArray: return index_array; case TypeObject: return index_token; default: break; } return -1; }