mirror of
https://github.com/Tencent/rapidjson.git
synced 2025-03-09 11:09:32 +01:00
Merge pull request #134 from Kosta-Github/Kosta/add_key_method
add `Key()` method to the `Handler` concept
This commit is contained in:
commit
5e03cbf1b3
@ -31,6 +31,7 @@ struct CapitalizeFilter {
|
||||
return out_.String(&buffer_.front(), length, true); // true = output handler need to copy the string
|
||||
}
|
||||
bool StartObject() { return out_.StartObject(); }
|
||||
bool Key(const char* str, SizeType length, bool copy) { return String(str, length, copy); }
|
||||
bool EndObject(SizeType memberCount) { return out_.EndObject(memberCount); }
|
||||
bool StartArray() { return out_.StartArray(); }
|
||||
bool EndArray(SizeType elementCount) { return out_.EndArray(elementCount); }
|
||||
|
@ -17,6 +17,10 @@ struct MyHandler {
|
||||
return true;
|
||||
}
|
||||
bool StartObject() { cout << "StartObject()" << endl; return true; }
|
||||
bool Key(const char* str, SizeType length, bool copy) {
|
||||
cout << "Key(" << str << ", " << length << ", " << boolalpha << copy << ")" << endl;
|
||||
return true;
|
||||
}
|
||||
bool EndObject(SizeType memberCount) { cout << "EndObject(" << memberCount << ")" << endl; return true; }
|
||||
bool StartArray() { cout << "StartArray()" << endl; return true; }
|
||||
bool EndArray(SizeType elementCount) { cout << "EndArray(" << elementCount << ")" << endl; return true; }
|
||||
|
@ -1386,7 +1386,7 @@ int z = a[0u].GetInt(); // This works too.
|
||||
if (!handler.StartObject())
|
||||
return false;
|
||||
for (ConstMemberIterator m = MemberBegin(); m != MemberEnd(); ++m) {
|
||||
if (!handler.String(m->name.GetString(), m->name.GetStringLength(), (m->name.flags_ & kCopyFlag) != 0))
|
||||
if (!handler.Key(m->name.GetString(), m->name.GetStringLength(), (m->name.flags_ & kCopyFlag) != 0))
|
||||
return false;
|
||||
if (!m->value.Accept(handler))
|
||||
return false;
|
||||
@ -1794,6 +1794,8 @@ private:
|
||||
|
||||
bool StartObject() { new (stack_.template Push<ValueType>()) ValueType(kObjectType); return true; }
|
||||
|
||||
bool Key(const Ch* str, SizeType length, bool copy) { return String(str, length, copy); }
|
||||
|
||||
bool EndObject(SizeType memberCount) {
|
||||
typename ValueType::Member* members = stack_.template Pop<typename ValueType::Member>(memberCount);
|
||||
stack_.template Top<ValueType>()->SetObjectRaw(members, (SizeType)memberCount, GetAllocator());
|
||||
|
@ -88,6 +88,8 @@ public:
|
||||
return Base::WriteStartObject();
|
||||
}
|
||||
|
||||
bool Key(const Ch* str, SizeType length, bool copy = false) { return String(str, length, copy); }
|
||||
|
||||
bool EndObject(SizeType memberCount = 0) {
|
||||
(void)memberCount;
|
||||
RAPIDJSON_ASSERT(Base::level_stack_.GetSize() >= sizeof(typename Base::Level));
|
||||
@ -135,6 +137,7 @@ public:
|
||||
|
||||
//! Simpler but slower overload.
|
||||
bool String(const Ch* str) { return String(str, internal::StrLen(str)); }
|
||||
bool Key(const Ch* str) { return Key(str, internal::StrLen(str)); }
|
||||
|
||||
//@}
|
||||
protected:
|
||||
|
@ -152,6 +152,7 @@ concept Handler {
|
||||
bool Double(double d);
|
||||
bool String(const Ch* str, SizeType length, bool copy);
|
||||
bool StartObject();
|
||||
bool Key(const Ch* str, SizeType length, bool copy);
|
||||
bool EndObject(SizeType memberCount);
|
||||
bool StartArray();
|
||||
bool EndArray(SizeType elementCount);
|
||||
@ -181,6 +182,7 @@ struct BaseReaderHandler {
|
||||
bool Double(double) { return static_cast<Override&>(*this).Default(); }
|
||||
bool String(const Ch*, SizeType, bool) { return static_cast<Override&>(*this).Default(); }
|
||||
bool StartObject() { return static_cast<Override&>(*this).Default(); }
|
||||
bool Key(const Ch* str, SizeType len, bool copy) { return static_cast<Override&>(*this).String(str, len, copy); }
|
||||
bool EndObject(SizeType) { return static_cast<Override&>(*this).Default(); }
|
||||
bool StartArray() { return static_cast<Override&>(*this).Default(); }
|
||||
bool EndArray(SizeType) { return static_cast<Override&>(*this).Default(); }
|
||||
@ -471,7 +473,7 @@ private:
|
||||
if (is.Peek() != '"')
|
||||
RAPIDJSON_PARSE_ERROR(kParseErrorObjectMissName, is.Tell());
|
||||
|
||||
ParseString<parseFlags>(is, handler);
|
||||
ParseString<parseFlags>(is, handler, true);
|
||||
RAPIDJSON_PARSE_ERROR_EARLY_RETURN_VOID;
|
||||
|
||||
SkipWhitespace(is);
|
||||
@ -617,26 +619,29 @@ private:
|
||||
|
||||
// Parse string and generate String event. Different code paths for kParseInsituFlag.
|
||||
template<unsigned parseFlags, typename InputStream, typename Handler>
|
||||
void ParseString(InputStream& is, Handler& handler) {
|
||||
void ParseString(InputStream& is, Handler& handler, bool isKey = false) {
|
||||
internal::StreamLocalCopy<InputStream> copy(is);
|
||||
InputStream& s(copy.s);
|
||||
|
||||
bool success = false;
|
||||
if (parseFlags & kParseInsituFlag) {
|
||||
typename InputStream::Ch *head = s.PutBegin();
|
||||
ParseStringToStream<parseFlags, SourceEncoding, SourceEncoding>(s, s);
|
||||
RAPIDJSON_PARSE_ERROR_EARLY_RETURN_VOID;
|
||||
size_t length = s.PutEnd(head) - 1;
|
||||
RAPIDJSON_ASSERT(length <= 0xFFFFFFFF);
|
||||
if (!handler.String((typename TargetEncoding::Ch*)head, SizeType(length), false))
|
||||
RAPIDJSON_PARSE_ERROR(kParseErrorTermination, s.Tell());
|
||||
const typename TargetEncoding::Ch* const str = (typename TargetEncoding::Ch*)head;
|
||||
success = (isKey ? handler.Key(str, SizeType(length), false) : handler.String(str, SizeType(length), false));
|
||||
}
|
||||
else {
|
||||
StackStream stackStream(stack_);
|
||||
ParseStringToStream<parseFlags, SourceEncoding, TargetEncoding>(s, stackStream);
|
||||
RAPIDJSON_PARSE_ERROR_EARLY_RETURN_VOID;
|
||||
if (!handler.String(stack_.template Pop<typename TargetEncoding::Ch>(stackStream.length_), stackStream.length_ - 1, true))
|
||||
RAPIDJSON_PARSE_ERROR(kParseErrorTermination, s.Tell());
|
||||
const typename TargetEncoding::Ch* const str = stack_.template Pop<typename TargetEncoding::Ch>(stackStream.length_);
|
||||
success = (isKey ? handler.Key(str, stackStream.length_ - 1, true) : handler.String(str, stackStream.length_ - 1, true));
|
||||
}
|
||||
if (!success)
|
||||
RAPIDJSON_PARSE_ERROR(kParseErrorTermination, s.Tell());
|
||||
}
|
||||
|
||||
// Parse string to an output is
|
||||
@ -1194,7 +1199,7 @@ private:
|
||||
}
|
||||
|
||||
case IterativeParsingMemberKeyState:
|
||||
ParseString<parseFlags>(is, handler);
|
||||
ParseString<parseFlags>(is, handler, true);
|
||||
if (HasParseError())
|
||||
return IterativeParsingErrorState;
|
||||
else
|
||||
|
@ -131,6 +131,8 @@ public:
|
||||
return WriteStartObject();
|
||||
}
|
||||
|
||||
bool Key(const Ch* str, SizeType length, bool copy = false) { return String(str, length, copy); }
|
||||
|
||||
bool EndObject(SizeType memberCount = 0) {
|
||||
(void)memberCount;
|
||||
RAPIDJSON_ASSERT(level_stack_.GetSize() >= sizeof(Level));
|
||||
@ -165,6 +167,7 @@ public:
|
||||
|
||||
//! Simpler but slower overload.
|
||||
bool String(const Ch* str) { return String(str, internal::StrLen(str)); }
|
||||
bool Key(const Ch* str) { return Key(str, internal::StrLen(str)); }
|
||||
|
||||
//@}
|
||||
|
||||
|
@ -819,9 +819,10 @@ struct IterativeParsingReaderHandler {
|
||||
const static int LOG_DOUBLE = -7;
|
||||
const static int LOG_STRING = -8;
|
||||
const static int LOG_STARTOBJECT = -9;
|
||||
const static int LOG_ENDOBJECT = -10;
|
||||
const static int LOG_STARTARRAY = -11;
|
||||
const static int LOG_ENDARRAY = -12;
|
||||
const static int LOG_KEY = -10;
|
||||
const static int LOG_ENDOBJECT = -11;
|
||||
const static int LOG_STARTARRAY = -12;
|
||||
const static int LOG_ENDARRAY = -13;
|
||||
|
||||
const static size_t LogCapacity = 256;
|
||||
int Logs[LogCapacity];
|
||||
@ -848,6 +849,8 @@ struct IterativeParsingReaderHandler {
|
||||
|
||||
bool StartObject() { RAPIDJSON_ASSERT(LogCount < LogCapacity); Logs[LogCount++] = LOG_STARTOBJECT; return true; }
|
||||
|
||||
bool Key (const Ch*, SizeType, bool) { RAPIDJSON_ASSERT(LogCount < LogCapacity); Logs[LogCount++] = LOG_KEY; return true; }
|
||||
|
||||
bool EndObject(SizeType c) {
|
||||
RAPIDJSON_ASSERT(LogCount < LogCapacity);
|
||||
Logs[LogCount++] = LOG_ENDOBJECT;
|
||||
@ -880,7 +883,7 @@ TEST(Reader, IterativeParsing_General) {
|
||||
handler.LOG_STARTARRAY,
|
||||
handler.LOG_INT,
|
||||
handler.LOG_STARTOBJECT,
|
||||
handler.LOG_STRING,
|
||||
handler.LOG_KEY,
|
||||
handler.LOG_STARTARRAY,
|
||||
handler.LOG_INT,
|
||||
handler.LOG_INT,
|
||||
@ -918,7 +921,7 @@ TEST(Reader, IterativeParsing_Count) {
|
||||
handler.LOG_STARTOBJECT,
|
||||
handler.LOG_ENDOBJECT, 0,
|
||||
handler.LOG_STARTOBJECT,
|
||||
handler.LOG_STRING,
|
||||
handler.LOG_KEY,
|
||||
handler.LOG_INT,
|
||||
handler.LOG_ENDOBJECT, 1,
|
||||
handler.LOG_STARTARRAY,
|
||||
|
Loading…
x
Reference in New Issue
Block a user