Hi!
I wish to concatenate two json objects and thought of this:
#include <json.hpp>
#include <iostream>
int main() {
nlohmann::json a,b;
a[ "sec" ] = {
{ "title", "some title" },
{ "cnt", 10 }
};
b[ "sec" ] = {
{ "more info", "add something more" }
};
a += b;
std::cout << a.dump(4);
}
which however throws an exception with v1.1.0. Any suggestions how to best do this?
Best, Mikael
The exception "cannot use push_back() with object" is due to the fact that a += b; is executed as a.push_back(b);, and push_back is only valid for arrays (see its documentation.)
(You originally reported a segmentation fault, and I was worried there was a bug ;-))
Unfortunately, the requested functionality is not present at this moment. Looking at Stack Overflow, it seems that std::map::insert can have similar effects. Maybe overloading nlohmann::json::insert accordingly could help. Any thoughts about this?
Thanks for quick response and sorry about the initial text; no bugs indeed! I actually do not know how to achieve what I want, regardless of syntax and I wonder if it's possible to add new objects to a["sec"] from another object? The insert() method does not allow objects if I understand it correctly. Concretely I have a json object created by a base class, and I need derived classes to add specific information to it.
I suppose STL-like merging using i.e. a.insert(b.begin(),b.end()) as for maps would be ideal, alternatively a << b?
Hi @mlund, you can achieve merging objects with the following function:
json merge(const json &a, const json &b)
{
json result = a.flatten();
json tmp = b.flatten();
for (json::iterator it = tmp.begin(); it != tmp.end(); ++it)
{
result[it.key()] = it.value();
}
return result.unflatten();
}
It is based on the flatten()/unflatten() functions and has the single limitation that empty arrays and objects are replaced by null.
I hope this helps!
Thanks! Alternatively, this also worked for my purpose:
for (auto it=b["sec"].begin(); it!=b["sec"].end(); it++)
a["sec"].push_back( json::object_t::value_type(it.key(), it.value()) );
Hi, is this usefull for include one json object into other? i've get some errors 馃槥
This basically implements the similar insert functions of std::map (http://en.cppreference.com/w/cpp/container/map/insert) and std::vector (http://en.cppreference.com/w/cpp/container/vector/insert).
Thats greate!
No, i need to concatenate one json object into a specific index of another, something like:
Entities["table"] = mergeJSON(Entities, ReadedEntity);
Where mergeJSON is the merge function what i getted from this topic.
How can i do that?
Could you provide an example for Entities and ReadedEntity?
Entities:
{"CSVMsg": {
"name": "PacketEntities",
"class":35,
"id":2,
"serial":782
}
}
ReadedEntity:
{"table":
{"name": "DC_Player",
"fields": {
"0": {"m_flSimulationTime": 47},
"1": {"m_nTickBase": 160748},
"2": {"m_vecOrigin": {
"0": 299.141327,
"1": 2343.210938
},
},
"3": {"m_vecOrigin2": -250.849808}
}
}
}
Need something like:
{"CSVMsg": {
"name": "PacketEntities",
"class":35,
"id":2,
"serial":782,
"table":
{"name": "DC_Player",
"fields": {
"0": {"m_flSimulationTime": 47},
"1": {"m_nTickBase": 160748},
"2": {"m_vecOrigin": {
"0": 299.141327,
"1": 2343.210938
},
},
"3": {"m_vecOrigin2": -250.849808}
}
}
}
}
For your example, the following should do:
Entities["CSVMsg"]["table"] = ReadedEntity["table"];
I don't test it already, but you are a kind of genius for my. Thank you a lot!
Hey
Not sure of how much of this is correct as I'm new to C++ but the original nlohmann post about merge produced issues with empty arrays as it converted them to null.. I did this little tweak to his code and now I can merge json files with empty arrays...
json merge(const json &a, const json &b)
{
json result = a;
json tmp = b;
for (json::iterator it = tmp.begin(); it != tmp.end(); ++it)
{
result[it.key()] = it.value();
}
return result;
}
We discuss a merge operation for objects in #661.
@Dariusz1989 FYI, the json tmp = b; there should not be necessary, you should just be able to use b directly to avoid copying b unnecessarily, which can be expensive.
Most helpful comment
Hi @mlund, you can achieve merging objects with the following function:
It is based on the
flatten()/unflatten()functions and has the single limitation that empty arrays and objects are replaced bynull.I hope this helps!