概述
JSON for Modern C++ 用起来方便,感觉跟使用动态语言JavaScript一样方便。举个例子
#include <iostream>
#include <iomanip>
#include <nlohmann/json.hpp>
using json = nlohmann::json;
int main()
{
// create a JSON object
json j =
{
{"pi", 3.141},
{"happy", true},
{"name", "Niels"},
{"nothing", nullptr},
{
"answer", {
{"everything", 42}
}
},
{"list", {1, 0, 2}},
{
"object", {
{"currency", "USD"},
{"value", 42.99}
}
}
};
// add new values
j["new"]["key"]["value"] = {"another", "list"};
// count elements
auto s = j.size();
j["size"] = s;
// pretty print with indent of 4 spaces
std::cout << std::setw(4) << j << '\n';
}
类型判断
nlohmann::json
提供了下列这些借口来判断内部实际的值是什么类型。
is_primitive , is_structured , is_null , is_boolean , is_number , is_number_integer ,
is_number_unsigned , is_number_float , is_object , is_array, is_string
其中 is_structured 是指 is_object() or is_array(),is_primitive 则是指 is_null() or is_string() or is_boolean() or is_number();
判断传进去的一个JSON字符串是不是一个 is_structured
json j = json::parse(jsonStr, nullptr, false); // 第三个参数是不要让 parse 抛异常
return j.is_structured();
判断key是否存在
// 方法一,单纯判断存不存在
json j_object = json::parse(R"( {"key": "value"} )");
std::cout << std::boolalpha << "j_object contains 'key': " << j_object.contains("key") << '\n'
// 方法二,返回迭代器,存在则可用迭代器取到对应的值
json j_object = {{"one", 1}, {"two", 2}};
auto it_two = j_object.find("two");
std::cout << std::boolalpha << "\"two\" was found: " << (it_two != j_object.end()) << '\n';
// 方法三,返回key的数目,存在返回1,不存在返回0
json j_object = {{"one", 1}, {"two", 2}};
auto count_two = j_object.count("two");
std::cout << "number of elements with key \"two\": " << count_two << '\n';
// 方法四,通过value方法获取,不存在返回默认的
json j =
{
{"integer", 1},
{"floating", 42.23},
{"string", "hello world"},
{"boolean", true},
{"object", {{"key1", 1}, {"key2", 2}}},
{"array", {1, 2, 3}}
};
int v_integer = j.value("integer", 0); // 存在,返回存在的 1
double v_floating = j.value("floating", 47.11);
std::string v_string = j.value("nonexisting", "oops"); // 不存在,返回默认的 oops
bool v_boolean = j.value("nonexisting", false);
std::cout << std::boolalpha << v_integer << " " << v_floating << " " << v_string << " " << v_boolean << "\n";
// 输出 1 42.23 oops false
获取key对应的value
// 获取指针类型
json value = 17;
auto p1 = value.get<json::number_integer_t*>();
// 获取值
json json_types =
{
{"boolean", true},
{
"number", {
{"integer", 42},
{"floating-point", 17.23}
}
}
};
auto v1 = json_types["boolean"].get<bool>();
auto v2 = json_types["number"]["integer"].get<int>();
auto v3 = json_types["number"]["integer"].get<short>();
// 获取引用
json value = 17;
// explicitly getting references
auto r1 = value.get_ref<const json::number_integer_t&>();
清空元素
json j_object = {{"one", 1}, {"two", 2}};
json j_array = {1, 2, 4, 8, 16};
j_object.clear();
j_array.clear();
std::cout << j_object << '\n';
std::cout << j_array << '\n';
// 输出
// {}
// []
序列化
auto j3 = json::parse("{ \"happy\": true, \"pi\": 3.141 }");
std::string s = j.dump(); // {\"happy\":true,\"pi\":3.141}
是不是没有元素存在
json j_object = {{"one", 1}, {"two", 2}};
json j_object_empty(json::value_t::object);
json j_array = {1, 2, 4, 8, 16};
json j_array_empty(json::value_t::array);
std::cout << j_object.empty() << '\n'; // false
std::cout << j_object_empty.empty() << '\n'; // true
std::cout << j_array.empty() << '\n'; // false
std::cout << j_array_empty.empty() << '\n'; // true
元素删除
json j_object = {{"one", 1}, {"two", 2}};
json j_array = {1, 2, 4, 8, 16};
// 范围删除
j_object.erase(j_object.find("two"), j_object.end()); // {"one":1}
j_array.erase(j_array.begin() + 1, j_array.begin() + 3); // [1,8,16]
// 单个删除
j_object.erase(j_object.find("two"));
// 以key删除,返回删除的个数
auto count_one = j_object.erase("one");
元素修改
// 插入
json j1 = {{"one", "eins"}, {"two", "zwei"}};
json j2 = {{"eleven", "elf"}, {"seventeen", "siebzehn"}};
j1.insert(j2.begin(), j2.end()); // {"eleven":"elf","one":"eins","seventeen":"siebzehn","two":"zwei"}
// 修改
j1["one"] = "hello";
// 增加
j1.push_back({"three", 3});
元素迭代
json j_object = {{"one", 1}, {"two", 2}};
json j_array = {1, 2, 4, 8, 16};
// example for an object
for (auto& x : j_object.items())
{
std::cout << "key: " << x.key() << ", value: " << x.value() << '\n';
}
// example for an array
for (auto& x : j_array.items())
{
std::cout << "key: " << x.key() << ", value: " << x.value() << '\n';
}
判断相等
json object_1 = {{"A", "a"}, {"B", "b"}};
json object_2 = {{"B", "b"}, {"A", "a"}};
std::cout << object_1 << " == " << object_2 << " " << (object_1 == object_2) << '\n';
元素长度
// create JSON values
json j_object = {{"one", 1}, {"two", 2}};
json j_object_empty(json::value_t::object);
json j_array = {1, 2, 4, 8, 16};
// call size()
std::cout << j_object.size() << '\n'; // 2
std::cout << j_object_empty.size() << '\n'; // 0
std::cout << j_array.size() << '\n'; // 5
元素类型
// create JSON values
json j_null;
json j_boolean = true;
json j_number_integer = -17;
json j_number_unsigned = 42u;
json j_number_float = 23.42;
json j_object = {{"one", 1}, {"two", 2}};
json j_array = {1, 2, 4, 8, 16};
json j_string = "Hello, world";
// call type() 都输出true
std::cout << std::boolalpha;
std::cout << (j_null.type() == json::value_t::null) << '\n';
std::cout << (j_boolean.type() == json::value_t::boolean) << '\n';
std::cout << (j_number_integer.type() == json::value_t::number_integer) << '\n';
std::cout << (j_number_unsigned.type() == json::value_t::number_unsigned) << '\n';
std::cout << (j_number_float.type() == json::value_t::number_float) << '\n';
std::cout << (j_object.type() == json::value_t::object) << '\n';
std::cout << (j_array.type() == json::value_t::array) << '\n';
std::cout << (j_string.type() == json::value_t::string) << '\n';