「生活可以更简单, 欢迎来到我的开源世界」
  1. 简单介绍
  2. 使用简介
    1. JSON as first-class data type
    2. Serialization / Deserialization(序列号/反序列化)
  3. 参考资料
JSON for Modern C++
2020-09-10
C++

JSON for Modern C++是一个简单且强大的json处理库,只需要包含一个头文件便可使用。

本文代码说明:单行注释解释代码,多行注释展示输出。

简单介绍

JSON for Modern C++有如下特点:

使用简介

JSON as first-class data type

#include <iostream>
#include <fstream>
#include <iomanip>
#include "json.hpp"

using namespace std;
using json = nlohmann::json;

int main(int argc, char **argv) {
// 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}
}}
};

cout << j.dump(4) << endl;
cout << j2.dump(4) << endl;
/* 相同的输出:
{
"answer": {
"everything": 42
},
"happy": true,
"list": [
1,
0,
2
],
"name": "Niels",
"nothing": null,
"object": {
"currency": "USD",
"value": 42.99
},
"pi": 3.141
}
*/
return 0;
}

一般情况无需声明json的值类型,但也支持显示声明特定的值类型:

#include <iostream>
#include <fstream>
#include <iomanip>
#include "json.hpp"

using namespace std;
using json = nlohmann::json;

int main(int argc, char **argv) {
// 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} });
cout << array_not_object.dump(4) << endl;
/*
[
[
"currency",
"USD"
],
[
"value",
42.99
]
]
*/
return 0;
}

Serialization / Deserialization(序列号/反序列化)

  1. json与string类型的转换

    #include <iostream>
    #include <fstream>
    #include <iomanip>
    #include "json.hpp"

    using namespace std;
    using json = nlohmann::json;

    int main(int argc, char **argv) {
    // 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("{ \"happy\": true, \"pi\": 3.141 }");

    cout << j.dump() << endl;
    cout << j2.dump() << endl;
    cout << j3.dump() << endl;
    /*
    {"happy":true,"pi":3.141}
    {"happy":true,"pi":3.141}
    {"happy":true,"pi":3.141}
    */
    return 0;
    }

    序列号与赋值的区别:

    #include <iostream>
    #include <fstream>
    #include <iomanip>
    #include "json.hpp"

    using namespace std;
    using json = nlohmann::json;

    int main(int argc, char **argv) {
    // store a string in a JSON value
    json j_string = "this is a string";

    // retrieve the string value
    auto cpp_string = j_string.get<std::string>();
    // retrieve the string value (alternative when an 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.get<std::string>() << '\n';
    // output of serialized value
    std::cout << j_string << " == " << serialized_string << std::endl;
    /*
    this is a string == this is a string == this is a string
    "this is a string" == "this is a string"
    */
    return 0;
    }

    dump()函数返回最初存储的字符串的值

    注意:该库仅支持UTF-8,当在库中存储不同编码的字符串时,调用dump()可能会抛出异常,除非异常json::error_handler_t::replace或json::error_handler_t::ignore被错误处理程序正确处理。

  2. json与stream类型的转换

    #include <iostream>
    #include <fstream>
    #include <iomanip>
    #include "json.hpp"

    using namespace std;
    using json = nlohmann::json;

    int main(int argc, char **argv) {
    // deserialize from standard input
    json j;
    std::cin >> j;

    // serialize to standard output
    std::cout << j << endl;

    // the setw manipulator was overloaded to set the indentation for pretty printing
    std::cout << std::setw(4) << j << std::endl;

    /*
    {"happy":true,"pi":3.141}
    {"happy":true,"pi":3.141}
    {
    "happy": true,
    "pi": 3.141
    }
    */

    // read a JSON file
    std::ifstream i("file.json");
    json j;
    i >> j;

    // write prettified JSON to another file
    std::ofstream o("pretty.json");
    o << std::setw(4) << j << std::endl;
    return 0;
    }
  3. 根据迭代器范围读取json

    如果迭代器的value_type是一个1、2或4字节的整型类型,那么它将分别被解释为UTF-8、UTF-16和UTF-32。

    #include <iostream>
    #include <fstream>
    #include <iomanip>
    #include "json.hpp"

    using namespace std;
    using json = nlohmann::json;

    int main(int argc, char **argv) {
    std::vector<std::uint8_t> v = {'t', 'r', 'u', 'e'};
    json j = json::parse(v.begin(), v.end());
    json j2 = json::parse(v);
    cout << j.dump() << endl;
    cout << j2.dump() << endl;
    /*
    true
    true
    */
    return 0;
    }
  4. 其他使用

    1. 自定义容器和迭代器
    2. SAX接口

参考资料

项目地址:JSON for Modern C++

json支持:json官网

<⇧>