1. 程式人生 > >RapidJson(V1.1.0)的Value簡單操作(拼接json串,存取檔案中的json,解析json串)

RapidJson(V1.1.0)的Value簡單操作(拼接json串,存取檔案中的json,解析json串)

#include <rapidjson/document.h>
#include <rapidjson/stringbuffer.h>
#include <rapidjson/pointer.h>
#include <rapidjson/writer.h>
#include <rapidjson/prettywriter.h>
#include <rapidjson/filereadstream.h>
//生成一串如下的json格式字串,並解析
// {
// "name":"qfl",
// "age":20,
// "letter":["a","b","c"],
// "location": {"province":"fujian","city":"xiamen","number":16}
// "book":[{"name":"book1", "isbn":"123"},{"name":"book2","isbn":"456"}],
// "healthy":true,
// }

//生成Json串
rapidjson::Document jsonDoc;    //生成一個dom元素Document
rapidjson::Document::AllocatorType &allocator = jsonDoc.GetAllocator(); //獲取分配器
jsonDoc.SetObject();    //將當前的Document設定為一個object,也就是說,整個Document是一個Object型別的dom元素

//新增屬性
jsonDoc.AddMember("name", "qfl", allocator);    //新增字串值
jsonDoc.AddMember("age", 20, allocator);        //新增int型別值

//生成array
rapidjson::Value letterArray(rapidjson::kArrayType);//建立一個Array型別的元素
letterArray.PushBack("a", allocator);
letterArray.PushBack("b", allocator);
letterArray.PushBack("c", allocator);
jsonDoc.AddMember("letter", letterArray, allocator);    //新增陣列

//生成一個object
rapidjson::Value locationObj(rapidjson::kObjectType);//建立一個Object型別的元素
locationObj.AddMember("province", "fujian", allocator);
locationObj.AddMember("city", "xiamen", allocator);
locationObj.AddMember("number", 16, allocator);
jsonDoc.AddMember("location", locationObj, allocator);  //新增object到Document中

//生成一個object陣列
rapidjson::Value bookArray(rapidjson::kArrayType);//生成一個Array型別的元素,用來存放Object
rapidjson::Value book1(rapidjson::kObjectType); //生成book1
book1.AddMember("name", "book1", allocator);
book1.AddMember("isbn", "123", allocator);
bookArray.PushBack(book1, allocator);           //新增到陣列

rapidjson::Value book2(rapidjson::kObjectType); //生成book2
book2.AddMember("name", "book2", allocator);
book2.AddMember("isbn", "456", allocator);
bookArray.PushBack(book2, allocator);           //新增到陣列
jsonDoc.AddMember("book", bookArray, allocator);

//新增屬性
jsonDoc.AddMember("healthy", true, allocator);  //新增bool型別值
// jsonDoc.AddMember("sports", NULL, allocator);//新增空值,這裡會導致報錯

//生成字串
rapidjson::StringBuffer buffer;
rapidjson::Writer<rapidjson::StringBuffer> writer(buffer);
jsonDoc.Accept(writer);

std::string strJson = std::string( buffer.GetString() );
printf("-----生成的Json:\n%s", strJson.c_str());

//寫到檔案
std::string strPath ="C:\\JsonFile.txt";
FILE* myFile = fopen(strPath.c_str(), "w");  //windows平臺要使用wb
if (myFile) 
{
	fputs(buffer.GetString(), myFile);
	fclose(myFile);
}


printf("-----讀取Json內容:\n");
//從檔案中讀取(注意和上面分開,不能確定檔案是否生成完畢,這裡讀取可能有問題)
rapidjson::Document newDoc;
std::string strPath ="C:\\JsonFile.txt";
FILE* myFile = fopen(strPath.c_str(), "r");   //windows平臺使用rb
if (myFile) 
{
	char buffer[256];
	FileReadStream inputStream(myFile,buffer,sizeof(buffer));  //建立一個輸入流
	newDoc.ParseStream<0>(inputStream); //將讀取的內容轉換為dom元素
	fclose(myFile); //關閉檔案,很重要
}
//判斷解析從流中讀取的字串是否有錯誤
if (newDoc.HasParseError()) 
{
	printf("Json Parse error:%d\n", newDoc.GetParseError()); //列印錯誤編號
}
else 
{
	//獲取json串中的資料
	//先判斷是否有這個欄位,如果使用不存在的key去取值會導致直接崩潰
	if (newDoc.HasMember("name")) 
	{
		printf("name:%s\n", newDoc["name"].GetString()); //必須要獲取對應的資料型別,rapidjson不會幫你轉換型別
	}
	else 
	{}

	if (newDoc.HasMember("age")) 
	{
		printf("age:%d\n", newDoc["age"].GetInt());  //獲取正確的型別
	}
	else 
	{}

	if (newDoc.HasMember("letter")) 
	{
		rapidjson::Value letter;    //使用一個新的rapidjson::Value來存放array的內容
		letter = newDoc["letter"];

		//確保它是一個Array,而且有內容
		if (letter.IsArray() && !letter.Empty()) 
		{
			//遍歷Array中的內容
			for (rapidjson::SizeType i = 0; i < letter.Size(); i++) 
			{
				printf("letter:%s\n", letter[i].GetString());
			}
		}
		else 
		{}
	}
	else {}

	if (newDoc.HasMember("location")) 
	{
		rapidjson::Value location;      //使用一個新的rapidjson::Value來存放object
		location = newDoc["location"];

		//確保它是一個Object
		if (location.IsObject()) 
		{

			if (location.HasMember("province")) 
			{
				printf("location:province:%s\n", location["province"].GetString());
			}
			else {}
			if (location.HasMember("city")) 
			{
				printf("location:city:%s\n", location["city"].GetString());
			}
			else {}
			if (location.HasMember("number")) 
			{
				printf("location:number:%d\n", location["number"].GetInt());
			}
			else {}
		}
		else {}
	}
	else {}

	//book是一個包含了2個object的array。按照上面的步驟來取值就行
	if (newDoc.HasMember("book")) 
	{
		rapidjson::Value book;
		book = newDoc["book"];

		//先取Array
		if (book.IsArray() && !book.Empty()) 
		{
			rapidjson::Value tempBook;
			for (rapidjson::SizeType i = 0; i < book.Size(); i++) 
			{
				tempBook = book[i]; //Array中每個元素又是一個Object

				if (tempBook.IsObject()) 
				{

					if (tempBook.HasMember("name") && tempBook.HasMember("isbn")) 
					{
						printf("book:%d:name:%s, isbn:%s\n", i, tempBook["name"].GetString(), tempBook["isbn"].GetString());
					}
					else {}
				}
				else {}
			}
		}
		else {}
	}
	else {}

	if (newDoc.HasMember("healthy")) 
	{
		if (newDoc["healthy"].GetBool()) 
		{
			printf("healthy:true\n");
		}
		else 
		{
			printf("healthy:false\n");
		}
	}
	else {}
}