介绍:
JSON 是常用的数据的一种格式, 各个语言或多或少都会用的 JSON 格式.
JSON http://www.json.org/ 是一个轻量级的数据定义格式, 比起 xml 易学易用, 而扩展功能不比 xml 差多少, 用之进行数据交换是一个很好的选择. JSON 的全称为: JavaScript Object Notation , 顾名思义, JSON 是用于标记 JavaScript 对象的.
编译方法:
使用 Jsoncpp 生成的 lib 文件:
首先下载 Jsoncpp 源码文件, 用 cmake 编译主目录中的 CMakeLists.txt, 之后打开 sln 文件, 进行编译, 会在 src\lib_json 文件夹中生成 Debug 和 Release 版本的 lib 文件.
在工程中引用, 只需要在链接器的附加依赖项中加入 lib 文件名, 附加库目录中添加 lib 路径, 之后 #include<JSON.h > 文件即可.
jsoncpp 使用详解
jsoncpp 主要包含三种类型的 class:Value,Reader,Writer.jsoncpp 中所有对象, 类名都在 namespace JSON 中, 包含 JSON.h 即可.
JSON::Value 只能处理 ANSI 类型的字符串, 如果 C++ 程序是用 Unicode 编码的, 最好加一个 Adapt 类来适配.
举例子之前首先推荐一个在线解析 JSON 格式 https://www.json.cn/ 的网站, 具体格式用法如下图所示:
之后根据这个格式进行 JSON 数据解析.
JSON 用法实例:
1) 从字符串中读取 JSON
- #include <string>
- #include <JSON/JSON.h>
- #include <iostream>
- #include <fstream>
- using namespace std;
- void readStrJson(); // 从字符串中读取 JSON
- void readStrProJson(); // 从字符串中读取 JSON(内容复杂些)
- int main(int argc, char *argv[])
- {
- readStrJson();
- cout <<"\n\n";
- readStrProJson();
- return 0;
- }
- // 从字符串中读取 JSON
- void readStrJson()
- {
- // 字符串
- const char* str =
- "{\"praenomen\":\"Gaius\",\"nomen\":\"Julius\",\"cognomen\":\"Caezar\","
- "\"born\":-100,\"died\":-44}";
- /*
- //JSON 内容如下:
- {
- "praenomen":"Gaius",
- "nomen":"Julius",
- "cognomen":"Caezar",
- "born":-100,
- "died":-44
- }
- */
- JSON::Reader reader;
- JSON::Value root;
- // 从字符串中读取数据
- if(reader.parse(str,root))
- {
- string praenomen = root["praenomen"].asString();
- string nomen = root["nomen"].asString();
- string cognomen = root["cognomen"].asString();
- int born = root["born"].asInt();
- int died = root["died"].asInt();
- cout << praenomen + "" + nomen +" " + cognomen
- << "was born in year" << born
- << ", died in year" << died << endl;
- }
- }
- // 从字符串中读取 JSON(内容复杂些)
- void readStrProJson()
- {
- string strValue = "{\"name\":\"json\",\"array\":[{\"cpp\":\"jsoncpp\"},{\"java\":\"jsoninjava\"},{\"php\":\"support\"}]}";
- /*
- //JSON 内容如下:
- {
- "name": "JSON″,
- "array": [
- {
- "cpp": "jsoncpp"
- },
- {
- "java": "jsoninjava"
- },
- {
- "php": "support"
- }
- ]
- }
- */
- JSON::Reader reader;
- JSON::Value value;
- if (reader.parse(strValue, value))
- {
- string out = value["name"].asString();
- cout << out << endl;
- const JSON::Value arrayObj = value["array"];
- for (unsigned int i = 0; i < arrayObj.size(); i++)
- {
- if (!arrayObj[i].isMember("cpp"))
- continue;
- out = arrayObj[i]["cpp"].asString();
- cout << out;
- if (i != (arrayObj.size() - 1))
- cout << endl;
- }
- }
- }
输出结果:
2) 从文件中读取 JSON
- #include <string>
- #include <JSON/JSON.h>
- #include <iostream>
- #include <fstream>
- using namespace std;
- void readFileJson(); // 从文件中读取 JSON, 一个存储了 JSON 格式字符串的文件
- int main(int argc, char *argv[])
- {
- readFileJson();
- return 0;
- }
- // 从文件中读取 JSON
- void readFileJson()
- {
- JSON::Reader reader;
- JSON::Value root;
- // 从文件中读取, 保证当前文件有 test.JSON 文件
- ifstream in("test.json", iOS::binary);
- //in.open("test.json", iOS::binary);
- if( !in.is_open() )
- {
- cout <<"Error opening file\n";
- return;
- }
- /*
- //test.JSON 内容如下:
- {
- "name":"Tsybius",
- "age":23,
- "sex_is_male":true,
- "partner":
- {
- "partner_name":"Galatea",
- "partner_age":21,
- "partner_sex_is_male":false
- },
- "achievement":["ach1","ach2","ach3"]
- }
- */
- if(reader.parse(in,root))
- {
- // 读取根节点信息
- string name = root["name"].asString();
- int age = root["age"].asInt();
- bool sex_is_male = root["sex_is_male"].asBool();
- cout << "My name is" << name << endl;
- cout << "I'm "<< age <<" years old" << endl;
- cout << "I'm a "<< (sex_is_male ?"man":"woman") << endl;
- // 读取子节点信息
- string partner_name = root["partner"]["partner_name"].asString();
- int partner_age = root["partner"]["partner_age"].asInt();
- bool partner_sex_is_male = root["partner"]["partner_sex_is_male"].asBool();
- cout << "My partner's name is " << partner_name << endl;
- cout << (partner_sex_is_male ? "he" : "she") << "is"
- << partner_age << "years old" << endl;
- // 读取数组信息
- cout << "Here's my achievements:" << endl;
- for(unsigned int i = 0; i < root["achievement"].size(); i++)
- {
- string ach = root["achievement"][i].asString();
- cout << ach << '\t';
- }
- cout << endl;
- cout << "Reading Complete!" << endl;
- }
- else
- {
- cout << "parse error\n" << endl;
- }
- in.close();
- }
3) 将信息保存为 JSON 格式
- #include <string>
- #include <JSON/JSON.h>
- #include <iostream>
- #include <fstream>
- using namespace std;
- void writeFileJson();// 将信息保存为 JSON 格式
- int main(int argc, char *argv[])
- {
- writeFileJson();
- return 0;
- }
- // 将信息保存为 JSON 格式
- void writeFileJson()
- {
- // 根节点
- JSON::Value root;
- // 根节点属性
- root["name"] = JSON::Value("Mike Jiang");
- root["age"] = JSON::Value(23);
- root["sex_is_male"] = JSON::Value(true);
- // 子节点
- JSON::Value partner;
- // 子节点属性
- partner["partner_name"] = JSON::Value("Galatea");
- partner["partner_age"] = JSON::Value(21);
- partner["partner_sex_is_male"] = JSON::Value(false);
- // 子节点挂到根节点上
- root["partner"] = JSON::Value(partner);
- // 数组形式
- root["achievement"].append("ach1");
- root["achievement"].append("ach2");
- root["achievement"].append("ach3");
- // 直接输出
- cout << "FastWriter:" << endl;
- JSON::FastWriter fw;
- cout << fw.write(root) << endl << endl;
- // 缩进输出
- cout << "StyledWriter:" << endl;
- JSON::StyledWriter sw;
- cout << sw.write(root) << endl << endl;
- // 输出到文件
- ofstream os;
- os.open("demo.json");
- os << sw.write(root);
- os.close();
- /*
- //JSON 文件内容如下:
- {
- "achievement" : [ "ach1", "ach2", "ach3" ],
- "age" : 23,
- "name" : "Mike Jiang",
- "partner" : {
- "partner_age" : 21,
- "partner_name" : "Galatea",
- "partner_sex_is_male" : false
- },
- "sex_is_male" : true
- }
- */
- }
输出结果:
demo.JSON 文件内容如下:
- {
- "achievement" : [ "ach1", "ach2", "ach3" ],
- "age" : 23,
- "name" : "Mike Jiang",
- "partner" : {
- "partner_age" : 21,
- "partner_name" : "Galatea",
- "partner_sex_is_male" : false
- },
- "sex_is_male" : true
- }
后记:
在 JSON 中检测某个字段是否存在的两个方法如下:
- if (root["url"].type() != JSON::nullValue){
- //url 字段存在
- }
- if(value["sex"].isNull()){
- //sex 字段存在
- }
以上就是常用的 JSON 语法, 后续有用的新的语法会继续补充.
更多参考: 一, 二, 三
来源: https://www.cnblogs.com/ZY-Dream/p/10054074.html