rapidjson初级使用之封装和解析
程序员文章站
2024-02-02 21:39:34
...
rapidjson超级好用,只需要包含头文件,也就是可以跨平台
虽然写很复杂的功能的时候可能需要自己封装一些接口,但是写简单的json解析完全够用了
rapidjson封装和解析
不多说,直接上代码(可以忽略操作文件的步骤),代码包含多种情况的json格式,搞清楚下面的几种格式,基本没什么问题了。
#include <iostream>
#include <string>
#include <fstream>
//包含rapidjson必要头文件,rapidjson文件夹拷贝到工程目录,或者设置include路径,或者加入到工程树
#include "rapidjson/document.h"
#include "rapidjson/filereadstream.h"
#include "rapidjson/filewritestream.h"
#include "rapidjson/prettywriter.h"
#include "rapidjson/stringbuffer.h"
using namespace std;
using namespace rapidjson; //引入rapidjson命名空间
//写json文件
void json_write()
{
Document doc;
doc.SetObject();
Document::AllocatorType &allocator=doc.GetAllocator(); //获取分配器
//1.添加字符串成员
doc.AddMember("author","tashaxing",allocator);
//2.添加数组成员
Value array1(kArrayType); //kArrayType 枚举成员 表示数组
for(int i=0;i<3;i++)
{
Value int_object(kObjectType);
int_object.SetInt(i);
array1.PushBack(int_object,allocator);
}
doc.AddMember("number",array1,allocator);
//3.添加复合对象
Value object(kObjectType); //kObjectType枚举成员 表示对象
object.AddMember("language1","C++",allocator);
object.AddMember("language2","java",allocator);
doc.AddMember("language",object,allocator);
//4.添加对象数组和复合对象的组合
Value array2(kArrayType);
Value object1(kObjectType);
object1.AddMember("hobby","drawing",allocator);
array2.PushBack(object1,allocator);
Value object2(kObjectType);
object2.AddMember("height",1.71,allocator);
array2.PushBack(object2,allocator);
doc.AddMember("information",array2,allocator);
StringBuffer buffer;
//PrettyWriter<StringBuffer> pretty_writer(buffer); //PrettyWriter是格式化的json(自动换行)
Writer<StringBuffer> pretty_writer(buffer); //Writer则是换行空格压缩后的json (换行和空格忽视)
doc.Accept(pretty_writer);
//打印到屏幕
cout<<"the json output:"<<endl;
cout<<buffer.GetString()<<endl;
//输出到文件
ofstream fout;
fout.open("test"); //可以使绝对和相对路径,用\\隔开目录,test, test.json, test.txt 都行,不局限于文件格式后缀,只要是文本文档
fout<<buffer.GetString();
fout.close();
}
//读json文件
void json_read()
{
cout<<"the json read:"<<endl;
ifstream fin;
fin.open("test");
string str;
string str_in="";
while(getline(fin,str)) //一行一行地读到字符串str_in中
{
str_in=str_in+str+'\n';
}
//解析并打印出来
Document document;
document.Parse<0>(str_in.c_str());
Value &node1=document["author"];
cout<<"author: "<<node1.GetString()<<endl;
Value &node2=document["number"];
cout<<"number: "<<endl;
if(node2.IsArray())
{
for(int i=0;i<node2.Size();i++)
cout<<'\t'<<node2[i].GetInt()<<endl;
}
Value &node3=document["language"]; //<<<这里要特别注意,取对象>>>
cout<<"language: "<<endl;
Value &tmp=node3["language1"]; //<<<这里是取子对象>>>
cout<<'\t'<<"language1: "<<tmp.GetString()<<endl; //<<<取子对象成员>>>
tmp=node3["language2"];
cout<<'\t'<<"language2: "<<tmp.GetString()<<endl;
Value &node4=document["information"];
cout<<"information: "<<endl;
if(node4.IsArray())
{
int i=0;
Value &data=node4[i]; //注意,此处下表索引只能用变量,不能用常量,例如node[0]编译错误
cout<<'\t'<<"hobby: "<<data["hobby"].GetString()<<endl;
i=1;
data=node4[i];
cout<<'\t'<<"height: "<<data["height"].GetDouble()<<endl;
}
}
int main(int argc,char **argv)
{
//写、读 测试
json_write();
json_read();
return 0;
}
运行结果(PrettyWriter):the json output:
{
"author": "tashaxing",
"number": [
0,
1,
2
],
"language": {
"language1": "C++",
"language2": "java"
},
"information": [
{
"hobby": "drawing"
},
{
"height": 1.71
}
]
}
the json read:
author: tashaxing
number:
0
1
2
language:
language1: C++
language2: java
information:
hobby: drawing
height: 1.71
运行结果(Writer):
the json output:
{"author":"tashaxing","number":[0,1,2],"language":{"language1":"C++","language2":"java"},"information":[{"hobby":"drawing"},{"height":1.71}]}
the json read:
author: tashaxing
number:
0
1
2
language:
language1: C++
language2: java
information:
hobby: drawing
height: 1.71
还有一种方法可以封装Json格式字符串:
#include "rapidjson/document.h"
#include "rapidjson/writer.h"
#include "rapidjson/stringbuffer.h"
#include "rapidjson/prettywriter.h"
#include <iostream>
#include <vector>
#include <string>
using namespace std;
using namespace rapidjson;
// json格式:{"RetCd":"0","RetMsg":"","row1":[{"key":1,"name":"aa"},...]}
struct AA{
int a;
string b;
};
int main()
{
vector<AA> para;
AA a;
a.a = 1;
a.b = "aa";
para.push_back(a);
a.a = 2;
a.b = "bb";
para.push_back(a);
a.a = 3;
a.b = "cc";
para.push_back(a);
//开始
StringBuffer buffer;
//Writer<StringBuffer> writer(buffer);
PrettyWriter<StringBuffer> writer(buffer);
writer.StartObject(); //根对象 开始
writer.Key("RetCd"); //键
writer.String("0"); //值
writer.Key("RetMsg");
writer.String("");
writer.Key("row1");
writer.StartArray(); //数组 开始
//....
for(int i = 0;i < para.size();i++){
writer.StartObject(); //子对象 开始
writer.Key("key");
writer.Int(para[i].a);
writer.Key("name");
writer.String(para[i].b.c_str());
writer.EndObject(); //子对象 结束
}
writer.EndArray(); //数组 结束
writer.EndObject(); //根对象 结束
printf("%s\n",buffer.GetString());
return 0;
}
运行结果:
{
"RetCd": "0",
"RetMsg": "",
"row1": [
{
"key": 1,
"name": "aa"
},
{
"key": 2,
"name": "bb"
},
{
"key": 3,
"name": "cc"
}
]
}
补充几个json的概念:
(1)标准json和非标准json:
标准json要求键必须都是双引号的字符串,而非标准json可以单引号。
例如:
{a : 'abc'}
{'a' : 'abc'}
{a : "abc"}
{"a" : "abc"}
只有第4个是标准json
(2)json中的[]与{}:
在 JSON 里 [] 是 Array {} 是Ojbect
[] Array 的key 是 int 从0算起
{} 的key 是 string
推荐阅读