文章目录
nlohmann/jsonjson介绍使用例子从文件中导入json对象使用json字面量创建json对象直接创建并操作json对象创建json arrayjson对象转stringstring转json对象像stl容器一样使用jsonstl容器转json arraystl容器转json object
限制字符集注释key的顺序
参考
nlohmann/json
nlohmann/json是一个使用现代c++编写的一个json库,该库是head-only的。
json介绍
关于json的介绍可以参考:CJSON简单介绍
使用
直接包含
single_include/
└── nlohmann
├── json_fwd.hpp
└── json.hpp
一般只要包含json.hpp,如果需要forward-declarations那么可以包含json_fwd.hpp。
注意,因为库使用了c++11特性,所以在编译的时候需要用C++11以上的标准编译。
#include
#include "include/single_include/nlohmann/json.hpp"
using json = nlohmann::json;
int main()
{
// create the different JSON values with default values
json j_null(json::value_t::null);
json j_boolean(json::value_t::boolean);
json j_number_integer(json::value_t::number_integer);
json j_number_float(json::value_t::number_float);
json j_object(json::value_t::object);
json j_array(json::value_t::array);
json j_string(json::value_t::string);
// serialize the JSON values
std::cout << j_null << '\n';
std::cout << j_boolean << '\n';
std::cout << j_number_integer << '\n';
std::cout << j_number_float << '\n';
std::cout << j_object << '\n';
std::cout << j_array << '\n';
std::cout << j_string << '\n';
}
运行结果:
$./a.out
null
false
0
0.0
{}
[]
""
例子
从文件中导入json对象
#include
#include
using json = nlohmann::json;
// ...
std::ifstream f("example.json");
json data = json::parse(f);
使用json字面量创建json对象
// Using (raw) string literals and json::parse
json ex1 = json::parse(R"(
{
"pi": 3.141,
"happy": true
}
)");
// Using user-defined (raw) string literals
using namespace nlohmann::literals;
json ex2 = R"(
{
"pi": 3.141,
"happy": true
}
)"_json;
// Using initializer lists
json ex3 = {
{"happy", true},
{"pi", 3.141},
};
直接创建并操作json对象
// create an empty structure (null)
json j;
// add a number that is stored as double (note the implicit conversion of j to an object)
j["pi"] = 3.141;
// add a Boolean that is stored as bool
j["happy"] = true;
// add a string that is stored as std::string
j["name"] = "Niels";
// add another null object by passing nullptr
j["nothing"] = nullptr;
// add an object inside the object
j["answer"]["everything"] = 42;
// add an array that is stored as std::vector (using an initializer list)
j["list"] = { 1, 0, 2 };
// add another object (using an initializer list of pairs)
j["object"] = { {"currency", "USD"}, {"value", 42.99} };
// instead, you could also write (which looks very similar to the JSON above)
json j2 = {
{"pi", 3.141},
{"happy", true},
{"name", "Niels"},
{"nothing", nullptr},
{"answer", {
{"everything", 42}
}},
{"list", {1, 0, 2}},
{"object", {
{"currency", "USD"},
{"value", 42.99}
}}
};
创建json array
// a way to express the empty array []
json empty_array_explicit = json::array();
// ways to express the empty object {}
json empty_object_implicit = json({});
json empty_object_explicit = json::object();
// a way to express an _array_ of key/value pairs [["currency", "USD"],
// ["value", 42.99]]
json array_not_object = json::array({{"currency", "USD"}, {"value", 42.99}});
std::cout << empty_array_explicit << '\n';
std::cout << empty_object_implicit << '\n';
std::cout << empty_object_explicit << '\n';
std::cout << array_not_object << '\n';
json对象转string
json j = "{ \"happy\": true, \"pi\": 3.141 }"_json;
// explicit conversion to string
std::string s = j.dump(); // {"happy":true,"pi":3.141}
// serialization with pretty printing
// pass in the amount of spaces to indent
std::cout << j.dump(4) << std::endl;
json j_string = "this is a string";
// retrieve the string value
auto cpp_string = j_string.template get
// retrieve the string value (alternative when a variable already exists)
std::string cpp_string2;
j_string.get_to(cpp_string2);
// retrieve the serialized value (explicit JSON serialization)
std::string serialized_string = j_string.dump();
// output of original string
std::cout << cpp_string << " == " << cpp_string2
<< " == " << j_string.template get
// output of serialized value
std::cout << j_string << " == " << serialized_string << std::endl;
// write prettified JSON to another file
std::ofstream o("pretty.json");
o << std::setw(4) << j << std::endl;
string转json对象
// create object from string literal
json j = "{ \"happy\": true, \"pi\": 3.141 }"_json;
// or even nicer with a raw string literal
auto j2 = R"(
{
"happy": true,
"pi": 3.141
}
)"_json;
// parse explicitly
auto j3 = json::parse(R"({"happy": true, "pi": 3.141})");
// store a string in a JSON value
json j_string = "this is a string";
std::cout << j3 << '\n';
std::cout << j_string << '\n';
// deserialize from standard input
json j_i;
std::cin >> j_i;
std::cout << j_i << '\n';
// the setw manipulator was overloaded to set the indentation for pretty
// printing
std::cout << std::setw(4) << j_i << std::endl;
// read a JSON file
std::ifstream i("example.json");
json j_s;
i >> j_s;
std::cout << j_s << '\n';
std::vector
json j_v = json::parse(v.begin(), v.end());
json j_v1 = json::parse(v);
std::cout << j_v << '\n';
std::cout << j_v1 << '\n';
像stl容器一样使用json
// create an array using push_back
json j;
j.push_back("foo");
j.push_back(1);
j.push_back(true);
std::cout << j << '\n';
// also use emplace_back
j.emplace_back(1.78);
std::cout << j << '\n';
// iterate the array
for (json::iterator it = j.begin(); it != j.end(); ++it) {
std::cout << *it << '\n';
}
// range-based for
for (auto &element : j) {
std::cout << element << '\n';
}
// getter/setter
const auto tmp = j[0].template get
j[1] = 42;
bool foo = j.at(2);
// comparison
std::cout << (j == R"(["foo", 1, true, 1.78])"_json) << '\n'; // true
// other stuff
std::cout << j.size() << '\n'; // 4 entries
j.empty(); // false
std::cout << typeid(j.type()).name() << '\n'; // json::value_t::array
j.clear(); // the array is empty again
// convenience type checkers
std::cout << j.is_null() << '\n';
std::cout << j.is_boolean() << '\n';
std::cout << j.is_number() << '\n';
std::cout << j.is_object() << '\n';
std::cout << j.is_array() << '\n';
std::cout << j.is_string() << '\n';
// create an object
json o;
o["foo"] = 23;
o["bar"] = false;
o["baz"] = 3.141;
std::cout << o << '\n';
// also use emplace
o.emplace("weather", "sunny");
std::cout << o << '\n';
// special iterator member functions for objects
for (json::iterator it = o.begin(); it != o.end(); ++it) {
std::cout << it.key() << " : " << it.value() << "\n";
}
// the same code as range for
for (auto &el : o.items()) {
std::cout << el.key() << " : " << el.value() << "\n";
}
// even easier with structured bindings (C++17)
for (auto &[key, value] : o.items()) {
std::cout << key << " : " << value << "\n";
}
// find an entry
if (o.contains("foo")) {
std::cout << R"(there is an entry with key "foo")" << '\n';
}
// or via find and an iterator
if (o.find("foo") != o.end()) {
std::cout << R"(there is an entry with key "foo")" << '\n';
}
// or simpler using count()
int foo_present = o.count("foo"); // 1
int fob_present = o.count("fob"); // 0
std::cout << foo_present << '\n';
std::cout << fob_present << '\n';
// delete an entry
o.erase("foo");
std::cout << o << '\n';
stl容器转json array
std::vector
json j_vec(c_vector);
std::cout << j_vec << '\n';
std::deque
json j_deque(c_deque);
std::cout << j_deque << '\n';
std::list
json j_list(c_list);
std::cout << j_list << '\n';
std::forward_list
34567890987654, 45678909876543};
json j_flist(c_flist);
std::cout << j_list << '\n';
std::array
json j_array(c_array);
std::cout << j_array << '\n';
std::set
json j_set(c_set); // only one entry for "one" is used
std::cout << j_set << '\n';
std::unordered_set
json j_uset(c_uset); // only one entry for "one" is used
std::cout << j_uset << '\n';
std::multiset
json j_mset(c_mset); // both entries for "one" are used
std::cout << j_mset << '\n';
std::unordered_multiset
json j_umset(c_umset); // both entries for "one" are used
std::cout << j_umset << '\n';
stl容器转json object
std::map
json j_map(c_map);
std::cout << j_map << '\n';
std::unordered_map
{"one", 1.2}, {"two", 2.3}, {"three", 3.4}};
json j_umap(c_umap);
std::cout << j_umap << '\n';
std::multimap
{"one", true}, {"two", true}, {"three", false}, {"three", true}};
json j_mmap(c_mmap); // only one entry for key "three" is used
std::cout << j_mmap << '\n';
std::unordered_multimap
{"one", true}, {"two", true}, {"three", false}, {"three", true}};
json j_ummap(c_ummap); // only one entry for key "three" is used
std::cout << j_ummap << '\n';
限制
字符集
只支持UTF-8作为输入
注释
不支持json注释
key的顺序
默认不保存json中key的顺序,即打印的key的顺序是随机的。如果要支持,使用nlohmann::ordered_json试试。
参考
https://json.nlohmann.me/ https://github.com/miloyip/nativejson-benchmark
推荐链接
发表评论