一区二区三区三上|欧美在线视频五区|国产午夜无码在线观看视频|亚洲国产裸体网站|无码成年人影视|亚洲AV亚洲AV|成人开心激情五月|欧美性爱内射视频|超碰人人干人人上|一区二区无码三区亚洲人区久久精品

0
  • 聊天消息
  • 系統(tǒng)消息
  • 評(píng)論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫文章/發(fā)帖/加入社區(qū)
會(huì)員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識(shí)你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示

使用cJSON庫(kù)來(lái)做數(shù)據(jù)組包及數(shù)據(jù)解析分享

Dp1040 ? 來(lái)源:嵌入式大雜燴 ? 2023-09-25 09:10 ? 次閱讀

JSON(JavaScript Object Notation)是一種輕量級(jí)的數(shù)據(jù)交換格式。JSON在互聯(lián)網(wǎng)相關(guān)開發(fā)中用得很多,在我們嵌入式中用得也不少。最近小編在項(xiàng)目中也有用到,分享分享。

簡(jiǎn)單的JSON格式數(shù)據(jù)如:

{
"name":"xxx",
"num":xxx,
"c_score":xxx
}

這里我們需要知道一個(gè)概念:鍵值對(duì)。比如:

"name":"xxx"

像這樣子的就是一對(duì)鍵值對(duì)。

當(dāng)我們作為發(fā)送方時(shí),我們要把xxx這些有用的數(shù)據(jù)組合成JSON格式的數(shù)據(jù)發(fā)送給接收方;當(dāng)我們作為接收方時(shí),我們需要從這一堆JSON數(shù)據(jù)中解析出xxx這些有用的數(shù)據(jù)拿來(lái)使用。

簡(jiǎn)單的JSON數(shù)據(jù),我們使用C語(yǔ)言的一些字符串操作相關(guān)的庫(kù)函數(shù)也是可以做到組包和解析的,但是一些稍微復(fù)雜一點(diǎn)的JSON,可能就沒那么好操作了。

這時(shí)候我們可以借助一個(gè)第三方庫(kù)——cJSON庫(kù),可以很方便來(lái)做數(shù)據(jù)組包及解析。

下面,我們通過(guò)實(shí)例來(lái)分享使用cJSON庫(kù)來(lái)做數(shù)據(jù)組包及數(shù)據(jù)解析。

一、組包與解析示例

1、確定協(xié)議數(shù)據(jù)

在實(shí)際開發(fā)中,要把JSON數(shù)據(jù)作為通信的數(shù)據(jù),自然要先確定通信雙方要交互的數(shù)據(jù)有哪些,如有需要還需編寫形成協(xié)議文檔。協(xié)議文檔包含要傳輸?shù)臄?shù)據(jù),數(shù)據(jù)類型等信息。

比如:

bc2e7e74-5b3b-11ee-939d-92fbcf53809c.png

2、組JSON數(shù)據(jù)包示例

從控制臺(tái)輸入一些學(xué)生信息,組合成字符串格式的JSON數(shù)據(jù)包,然后再輸出至控制臺(tái)。

操作示例:

bc539ff6-5b3b-11ee-939d-92fbcf53809c.png

首先,我們先從倉(cāng)庫(kù)下載cJSON源碼,文件夾內(nèi)容如:

bc696296-5b3b-11ee-939d-92fbcf53809c.png

我們只需要把cJSON.c、cJSON.h兩個(gè)文件復(fù)制到我們工程的根目錄下就可以使用,如:

bc82b0c0-5b3b-11ee-939d-92fbcf53809c.png

從cJSON.h可以看到其給我們提供了很多接口:

bc91fff8-5b3b-11ee-939d-92fbcf53809c.png

本例中我們重點(diǎn)關(guān)注如下幾個(gè)接口即可:

cJSON_CreateObject:創(chuàng)建JSON對(duì)象,{}擴(kuò)起來(lái)的
cJSON_CreateString:創(chuàng)建字符串
cJSON_CreateNumber:創(chuàng)建int類型數(shù)據(jù)
cJSON_AddItemToObject:添加到JSON對(duì)象中
cJSON_Print:呈現(xiàn)為標(biāo)準(zhǔn)的JSON格式
cJSON_PrintUnformatted:呈現(xiàn)為去掉空格的JSON格式
cJSON_Delete:JSON對(duì)象刪除,做一些釋放內(nèi)存的工作

我們創(chuàng)建的的組包函數(shù)如下:

staticchar*StudentsData_Packet(pStudentDef _Stu)
{
char*res_string=NULL;//返回值
cJSON*name=NULL;//名字
cJSON*num=NULL;//學(xué)號(hào)
cJSON*c_score=NULL;//C語(yǔ)言分?jǐn)?shù)

/*創(chuàng)建一個(gè)JSON對(duì)象,{}擴(kuò)起來(lái)*/
cJSON*obj=cJSON_CreateObject();
if(obj==NULL)
{
gotoend;
}

/*創(chuàng)建"name":"xxx"鍵值對(duì)*/
name=cJSON_CreateString(_Stu->name);
if(name==NULL)
{
gotoend;
}
cJSON_AddItemToObject(obj,"name",name);

/*創(chuàng)建"num":207鍵值對(duì)*/
num=cJSON_CreateNumber(_Stu->num);
if(name==NULL)
{
gotoend;
}
cJSON_AddItemToObject(obj,"num",num);

/*創(chuàng)建"c_score":95鍵值對(duì)*/
c_score=cJSON_CreateNumber(_Stu->c_score);
if(name==NULL)
{
gotoend;
}
cJSON_AddItemToObject(obj,"c_score",c_score);

res_string=cJSON_Print(obj);//呈現(xiàn)為JSON格式
//res_string=cJSON_PrintUnformatted(obj);//呈現(xiàn)為無(wú)格式

if(res_string==NULL)
{
fprintf(stderr,"Failed to print monitor.
");
}

/*異常情況統(tǒng)一Delete(free)*/
end:
cJSON_Delete(obj);
returnres_string;
}

詳細(xì)解釋見注釋。我們重點(diǎn)看一下cJSON_Print與cJSON_PrintUnformatted這兩個(gè)接口。

這兩個(gè)接口的差別就是組合成的JSON數(shù)據(jù)是否有空格。

有空格的JSON數(shù)據(jù),即用cJSON_Print時(shí)的效果為:

bca850be-5b3b-11ee-939d-92fbcf53809c.png

無(wú)空格的JSON數(shù)據(jù),即用cJSON_PrintUnformatted時(shí)的效果為:

bcb8c1a6-5b3b-11ee-939d-92fbcf53809c.png

如果想要輸出查看時(shí),當(dāng)然是用cJSON_Print比較方便查看;如果是實(shí)際通信時(shí),當(dāng)然是用cJSON_PrintUnformatted會(huì)比較好,畢竟去掉空格就可以減小一定程度的通信負(fù)擔(dān)。

完整代碼:

/*
作者:ZhengN
公眾號(hào):嵌入式大雜燴
*/

#include
#include
#include
#include"cJSON.h"

#defineSTU_NAME_LEN32

/*學(xué)生結(jié)構(gòu)體*/
typedefstruct_Student
{
charname[STU_NAME_LEN];//名字
intnum;//學(xué)號(hào)
intc_score;//C語(yǔ)言分?jǐn)?shù)
}StudentDef,*pStudentDef;

/*內(nèi)部函數(shù)聲明*/
staticchar*StudentsData_Packet(pStudentDef _Stu);

/********************************************************************************************************
**函數(shù):main
**------------------------------------------------------------------------------------------------------
**參數(shù):
**說(shuō)明:
**返回:
********************************************************************************************************/
intmain(void)
{
charname[STU_NAME_LEN]={0};
intnum=0;
intc_score=0;
StudentDef stu;
intstu_count=0;
inti=0;

/*學(xué)生總?cè)藬?shù)*/
printf("Please input number of student:");
scanf("%d",&stu_count);

while(i++name);
if(name==NULL)
{
gotoend;
}
cJSON_AddItemToObject(obj,"name",name);

/*創(chuàng)建"num":207鍵值對(duì)*/
num=cJSON_CreateNumber(_Stu->num);
if(name==NULL)
{
gotoend;
}
cJSON_AddItemToObject(obj,"num",num);

/*創(chuàng)建"c_score":95鍵值對(duì)*/
c_score=cJSON_CreateNumber(_Stu->c_score);
if(name==NULL)
{
gotoend;
}
cJSON_AddItemToObject(obj,"c_score",c_score);

res_string=cJSON_Print(obj);//呈現(xiàn)為JSON格式
//res_string=cJSON_PrintUnformatted(obj);//呈現(xiàn)為無(wú)格式

if(res_string==NULL)
{
fprintf(stderr,"Failed to print monitor.
");
}

/*異常情況統(tǒng)一Delete(free)*/
end:
cJSON_Delete(obj);
returnres_string;
}

3、解析JSON數(shù)據(jù)包示例

我們把我們想要解析的數(shù)據(jù)放到一個(gè)student_data.txt文件中,然后讀取其內(nèi)容拿來(lái)解析,最后輸出解析結(jié)果。

student_data.txt的內(nèi)容如:

bcc62526-5b3b-11ee-939d-92fbcf53809c.png

解析結(jié)果:

bcccb490-5b3b-11ee-939d-92fbcf53809c.png

關(guān)于這個(gè)示例我們需要關(guān)注的接口有:

cJSON_Parse:JSON解析函數(shù),解析{}得到里面的內(nèi)容
cJSON_GetObjectItemCaseSensitive:從對(duì)象中獲取鍵“字符串”。不分大小寫
cJSON_IsString:判斷是否是字符串
cJSON_IsNumber:判斷是否是整形數(shù)
cJSON_Delete:JSON對(duì)象刪除,做一些釋放內(nèi)存的工作

我們創(chuàng)建的解析函數(shù)如下:

staticvoidStudentsData_Parse(pStudentDef _Stu,constchar*_JsonStudnetData)
{
cJSON*student_json=NULL;//student_json操作對(duì)象,可代表{}擴(kuò)起來(lái)的內(nèi)容
cJSON*name=NULL;
cJSON*num=NULL;
cJSON*c_score=NULL;

/*開始解析*/
student_json=cJSON_Parse(_JsonStudnetData);
if(NULL==student_json)
{
constchar*error_ptr=cJSON_GetErrorPtr();
if(error_ptr!=NULL)
{
fprintf(stderr,"Error before:%s
",error_ptr);
}
gotoend;
}

/*解析獲取name得值*/
name=cJSON_GetObjectItemCaseSensitive(student_json,"name");
if(cJSON_IsString(name)&&(name->valuestring!=NULL))
{
memcpy(&_Stu->name,name->valuestring,strlen(name->valuestring));
}

/*解析獲取num的值*/
num=cJSON_GetObjectItemCaseSensitive(student_json,"num");
if(cJSON_IsNumber(num))
{
_Stu->num=num->valueint;
}

/*解析獲取c_score的值*/
c_score=cJSON_GetObjectItemCaseSensitive(student_json,"c_score");
if(cJSON_IsNumber(c_score))
{
_Stu->c_score=c_score->valueint;
}

end:
cJSON_Delete(student_json);
}

解釋見注釋。

完整代碼:

/*
作者:ZhengN
公眾號(hào):嵌入式大雜燴
*/
#include
#include
#include
#include"cJSON.h"

#defineSTU_NAME_LEN32

/*學(xué)生結(jié)構(gòu)體*/
typedefstruct_Student
{
charname[STU_NAME_LEN];//名字
intnum;//學(xué)號(hào)
intc_score;//C語(yǔ)言分?jǐn)?shù)
}StudentDef,*pStudentDef;

/*內(nèi)部函數(shù)聲明*/
staticvoidStudentsData_Parse(pStudentDef _Stu,constchar*_JsonStudnetData);
staticvoidPrintParseResult(constpStudentDef _Stu);

/********************************************************************************************************
**函數(shù):main
**------------------------------------------------------------------------------------------------------
**參數(shù):
**說(shuō)明:
**返回:
********************************************************************************************************/
intmain(void)
{
StudentDef stu={0};//保存解析后的數(shù)據(jù)
intfile_len=0;//文件長(zhǎng)度
FILE*fp=NULL;//文件句柄
char*data=NULL;//用于保存從文件讀出的數(shù)據(jù)

/*文件操作*/
if((fp=fopen("student_data.txt","r"))==NULL)
{
printf("Open file error!
");
exit(EXIT_FAILURE);
}
fseek(fp,0,SEEK_END);//文件位置指針指向文件末尾
file_len=ftell(fp);//獲取文末相對(duì)于文首的偏移值
fseek(fp,0,SEEK_SET);//文件位置指針指向文首
data=(char*)malloc(file_len+1);//為data申請(qǐng)堆內(nèi)存
fread(data,file_len,1,fp);//讀取文件數(shù)據(jù)保存至data
fclose(fp);//關(guān)閉文件

/*解析*/
StudentsData_Parse(&stu,(constchar*)data);

/*打印輸出解析結(jié)果*/
PrintParseResult(&stu);

/*釋放內(nèi)存*/
free(data);//防止內(nèi)存泄漏
data=NULL;//防止出現(xiàn)野指針

return0;
}

/********************************************************************************************************
**函數(shù):StudentsData_Parse,JOSN格式學(xué)生期末數(shù)據(jù)解析
**------------------------------------------------------------------------------------------------------
**參數(shù):_JsonStudnetData:JSON數(shù)據(jù)_Stu:保存解析出的有用數(shù)據(jù)
**說(shuō)明:
**返回:
********************************************************************************************************/
staticvoidStudentsData_Parse(pStudentDef _Stu,constchar*_JsonStudnetData)
{
cJSON*student_json=NULL;//student_json操作對(duì)象,可代表{}擴(kuò)起來(lái)的內(nèi)容
cJSON*name=NULL;
cJSON*num=NULL;
cJSON*c_score=NULL;

/*開始解析*/
student_json=cJSON_Parse(_JsonStudnetData);
if(NULL==student_json)
{
constchar*error_ptr=cJSON_GetErrorPtr();
if(error_ptr!=NULL)
{
fprintf(stderr,"Error before:%s
",error_ptr);
}
gotoend;
}

/*解析獲取name得值*/
name=cJSON_GetObjectItemCaseSensitive(student_json,"name");
if(cJSON_IsString(name)&&(name->valuestring!=NULL))
{
memcpy(&_Stu->name,name->valuestring,strlen(name->valuestring));
}

/*解析獲取num的值*/
num=cJSON_GetObjectItemCaseSensitive(student_json,"num");
if(cJSON_IsNumber(num))
{
_Stu->num=num->valueint;
}

/*解析獲取c_score的值*/
c_score=cJSON_GetObjectItemCaseSensitive(student_json,"c_score");
if(cJSON_IsNumber(c_score))
{
_Stu->c_score=c_score->valueint;
}

end:
cJSON_Delete(student_json);
}

/********************************************************************************************************
**函數(shù):PrintParseResult,打印輸出解析結(jié)果
**------------------------------------------------------------------------------------------------------
**參數(shù):
**說(shuō)明:
**返回:
********************************************************************************************************/
staticvoidPrintParseResult(constpStudentDef _Stu)
{
printf("name:%s,num:%d,c_score:%d
",_Stu->name,_Stu->num,_Stu->c_score);
}

二、綜合示例

上一節(jié)中我們的組包、解析demo都是分開測(cè)試的,這一節(jié)再分享一個(gè)兩個(gè)demo綜合起來(lái)的demo:

bcd6c980-5b3b-11ee-939d-92fbcf53809c.png

運(yùn)行演示:

bcdd8b26-5b3b-11ee-939d-92fbcf53809c.gif

bcf48f60-5b3b-11ee-939d-92fbcf53809c.png

bd139810-5b3b-11ee-939d-92fbcf53809c.png

json_print.c完整代碼:

/*
作者:ZhengN
公眾號(hào):嵌入式大雜燴
*/
#include
#include
#include
#include
#include"cJSON.h"

#defineSTU_NAME_LEN32

/*學(xué)生結(jié)構(gòu)體*/
typedefstruct_Student
{
charname[STU_NAME_LEN];//名字
intnum;//學(xué)號(hào)
intc_score;//C語(yǔ)言分?jǐn)?shù)
}StudentDef,*pStudentDef;

/*內(nèi)部函數(shù)聲明*/
staticStudentDefStudentData_Prepare(void);
staticchar*StudentsData_Packet(pStudentDef _Stu);
staticvoidStudentData_Send(constchar*_data);

/********************************************************************************************************
**函數(shù):main
**------------------------------------------------------------------------------------------------------
**參數(shù):
**說(shuō)明:
**返回:
********************************************************************************************************/
intmain(void)
{
StudentDef stu={0};
char*stu_data=NULL;
intstu_count=0;
inti=0;

/*需要登記的學(xué)生總?cè)藬?shù)*/
printf("Please input number of student:");
scanf("%d",&stu_count);

while(i++name);
if(name==NULL)
{
gotoend;
}
cJSON_AddItemToObject(obj,"name",name);

/*創(chuàng)建"num":207鍵值對(duì)*/
num=cJSON_CreateNumber(_Stu->num);
if(name==NULL)
{
gotoend;
}
cJSON_AddItemToObject(obj,"num",num);

/*創(chuàng)建"c_score":95鍵值對(duì)*/
c_score=cJSON_CreateNumber(_Stu->c_score);
if(name==NULL)
{
gotoend;
}
cJSON_AddItemToObject(obj,"c_score",c_score);

res_string=cJSON_Print(obj);//呈現(xiàn)為JSON格式
//res_string=cJSON_PrintUnformatted(obj);//呈現(xiàn)為無(wú)格式

if(res_string==NULL)
{
fprintf(stderr,"Failed to print monitor.
");
}

/*異常情況統(tǒng)一Delete(free)*/
end:
cJSON_Delete(obj);
returnres_string;
}

/********************************************************************************************************
**函數(shù):StudentData_Send,JSON格式字符串?dāng)?shù)據(jù)組包發(fā)送
**------------------------------------------------------------------------------------------------------
**參數(shù):_data:要發(fā)送的數(shù)據(jù)
**說(shuō)明:
**返回:
********************************************************************************************************/
staticvoidStudentData_Send(constchar*_data)
{
WSADATA wd;
  SOCKET ClientSock;
  SOCKADDR_INServerSockAddr;

printf("%s

",_data);

  /*初始化操作sock需要的DLL*/
  WSAStartup(MAKEWORD(2,2),&wd);

  /*向服務(wù)端發(fā)起請(qǐng)求*/
memset(&ServerSockAddr,0,sizeof(ServerSockAddr));
ServerSockAddr.sin_family=AF_INET;
ServerSockAddr.sin_addr.s_addr=inet_addr("127.0.0.1");
ServerSockAddr.sin_port=htons(1314);

/*創(chuàng)建客戶端socket*/
if(-1==(ClientSock=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP)))
{
printf("socket error!
");
exit(EXIT_FAILURE);
}
if(-1==connect(ClientSock,(SOCKADDR*)&ServerSockAddr,sizeof(SOCKADDR)))
{
printf("connect error!
");
exit(EXIT_FAILURE);
}

/*發(fā)送數(shù)據(jù)到服務(wù)端*/
send(ClientSock,_data,strlen(_data),0);

/*關(guān)閉套接字*/
closesocket(ClientSock);
}

json_parse.c完整代碼:

左右滑動(dòng)查看全部代碼>>>

/*
作者:ZhengN
公眾號(hào):嵌入式大雜燴
*/
#include
#include
#include
#include
#include"cJSON.h"

#defineSTU_NAME_LEN32

/*學(xué)生結(jié)構(gòu)體*/
typedefstruct_Student
{
charname[STU_NAME_LEN];//名字
intnum;//學(xué)號(hào)
intc_score;//C語(yǔ)言分?jǐn)?shù)
}StudentDef,*pStudentDef;

/*內(nèi)部函數(shù)聲明*/
staticchar*StudentsData_Recv(void);
staticvoidStudentsData_Parse(pStudentDef _Stu,constchar*_JsonStudnetData);
staticvoidPrintParseResult(constpStudentDef _Stu);
staticvoidSaveParseResult(constpStudentDef _Stu);

/*內(nèi)部全局變量*/
staticFILE*stu_fp=NULL;

/********************************************************************************************************
**函數(shù):main
**------------------------------------------------------------------------------------------------------
**參數(shù):
**說(shuō)明:
**返回:
********************************************************************************************************/
intmain(void)
{
StudentDef stu={0};
char*recv_data;

while(1)
{
/*接收數(shù)據(jù)*/
recv_data=StudentsData_Recv();

/*解析*/
StudentsData_Parse(&stu,(constchar*)recv_data);

/*打印輸出解析結(jié)果*/
PrintParseResult(&stu);

/*保存數(shù)據(jù)到文件*/
SaveParseResult(&stu);

/*釋放內(nèi)存*/
free(recv_data);//防止內(nèi)存泄漏
recv_data=NULL;//防止出現(xiàn)野指針
}

return0;
}

/********************************************************************************************************
**函數(shù):StudentsData_Recv,接收數(shù)據(jù)
**------------------------------------------------------------------------------------------------------
**參數(shù):
**說(shuō)明:
**返回:
********************************************************************************************************/
staticchar*StudentsData_Recv(void)
{
WSADATA wd;
  SOCKADDR_IN ServerSockAddr;
intrecv_len=0;
char*recv_buf=(char*)malloc(512);
staticSOCKET ServerSock,ClientSock;
staticSOCKADDR ClientAddr;
staticintaddr_size=0;
staticintrun_count=0;

/*以下操作執(zhí)行只一次就可以*/
if(0==run_count)
{
/*初始化操作sock需要的DLL*/
WSAStartup(MAKEWORD(2,2),&wd);

/*創(chuàng)建服務(wù)端socket*/
if(-1==(ServerSock=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP)))
{
printf("server socket error!
");
exit(EXIT_FAILURE);
}

/*設(shè)置服務(wù)端信息*/
memset(&ServerSockAddr,0,sizeof(ServerSockAddr));//給結(jié)構(gòu)體ServerSockAddr清零
ServerSockAddr.sin_family=AF_INET;//使用IPv4地址
ServerSockAddr.sin_addr.s_addr=inet_addr("127.0.0.1");//本機(jī)IP地址
ServerSockAddr.sin_port=htons(1314);//端口

/*綁定套接字*/
if(-1==bind(ServerSock,(SOCKADDR*)&ServerSockAddr,sizeof(SOCKADDR)))
{
printf("bind error!
");
exit(EXIT_FAILURE);
}

printf("bind ok!
");
/*進(jìn)入監(jiān)聽狀態(tài)*/
if(-1==listen(ServerSock,10))
{
printf("listen error!
");
exit(EXIT_FAILURE);
}
printf("listen ok!
");

addr_size=sizeof(SOCKADDR);
}

run_count++;

/*監(jiān)聽客戶端請(qǐng)求,accept函數(shù)返回一個(gè)新的套接字,發(fā)送和接收都是用這個(gè)套接字*/
if(-1==(ClientSock=accept(ServerSock,(SOCKADDR*)&ClientAddr,&addr_size)))
{
printf("client socket error!
");
exit(EXIT_FAILURE);
}

/*接受客戶端的返回?cái)?shù)據(jù)*/
memset(recv_buf,0,512);
recv_len=recv(ClientSock,recv_buf,512,0);
printf("%s
",recv_buf);

/*關(guān)閉客戶端套接字*/
closesocket(ClientSock);

/*返回獲取得到JSON數(shù)據(jù)*/
return(char*)recv_buf;
}

/********************************************************************************************************
**函數(shù):StudentsData_Parse,JOSN格式學(xué)生期末數(shù)據(jù)解析
**------------------------------------------------------------------------------------------------------
**參數(shù):_JsonStudnetData:JSON數(shù)據(jù)_Stu:保存解析出的有用數(shù)據(jù)
**說(shuō)明:
**返回:
********************************************************************************************************/
staticvoidStudentsData_Parse(pStudentDef _Stu,constchar*_JsonStudnetData)
{
cJSON*student_json=NULL;//student_json操作對(duì)象,可代表{}擴(kuò)起來(lái)的內(nèi)容
cJSON*name=NULL;
cJSON*num=NULL;
cJSON*c_score=NULL;

/*開始解析*/
student_json=cJSON_Parse(_JsonStudnetData);
if(NULL==student_json)
{
constchar*error_ptr=cJSON_GetErrorPtr();
if(error_ptr!=NULL)
{
fprintf(stderr,"Error before:%s
",error_ptr);
}
gotoend;
}

/*解析獲取name得值*/
name=cJSON_GetObjectItemCaseSensitive(student_json,"name");
if(cJSON_IsString(name)&&(name->valuestring!=NULL))
{
memset(&_Stu->name,0,STU_NAME_LEN*sizeof(char));
memcpy(&_Stu->name,name->valuestring,strlen(name->valuestring));
}

/*解析獲取num的值*/
num=cJSON_GetObjectItemCaseSensitive(student_json,"num");
if(cJSON_IsNumber(num))
{
_Stu->num=num->valueint;
}

/*解析獲取c_score的值*/
c_score=cJSON_GetObjectItemCaseSensitive(student_json,"c_score");
if(cJSON_IsNumber(c_score))
{
_Stu->c_score=c_score->valueint;
}

end:
cJSON_Delete(student_json);
}

/********************************************************************************************************
**函數(shù):PrintParseResult,打印輸出解析結(jié)果
**------------------------------------------------------------------------------------------------------
**參數(shù):
**說(shuō)明:
**返回:
********************************************************************************************************/
staticvoidPrintParseResult(constpStudentDef _Stu)
{
printf("name:%s,num:%d,c_score:%d

",_Stu->name,_Stu->num,_Stu->c_score);
}

/********************************************************************************************************
**函數(shù):SaveParseResult,保存解析結(jié)果
**------------------------------------------------------------------------------------------------------
**參數(shù):_Stu:需要保存的數(shù)據(jù)
**說(shuō)明:
**返回:
********************************************************************************************************/
staticvoidSaveParseResult(constpStudentDef _Stu)
{
charwrite_buf[512]={0};
staticintstu_count=0;

/*以可在文件末尾追加內(nèi)容的方式打開文件*/
  if((stu_fp=fopen("ParseResult.txt","a+"))==NULL)
  {
   printf("Open file error!
");
   returnexit(EXIT_FAILURE);
  }

/*按指定格式寫入文件*/
snprintf(write_buf,512,"name:%s,num:%d,c_score:%d
",_Stu->name,_Stu->num,_Stu->c_score);
size_tlen=fwrite((char*)write_buf,1,strlen(write_buf),stu_fp);

/*文件位置指針偏移*/
fseek(stu_fp,len*stu_count,SEEK_SET);
stu_count++;

/*關(guān)閉文件*/
fclose(stu_fp);
}

編譯命令:

左右滑動(dòng)查看全部代碼>>>

gcc json_print.c cJSON.c-o json_print.exe-lwsocket32
gcc json_parse.c cJSON.c-o json_parse.exe-lwsocket32

綜合demo加了socket相關(guān)代碼,本篇筆記主要介紹JSON數(shù)據(jù)的組包及解析。






審核編輯:劉清

聲明:本文內(nèi)容及配圖由入駐作者撰寫或者入駐合作網(wǎng)站授權(quán)轉(zhuǎn)載。文章觀點(diǎn)僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場(chǎng)。文章及其配圖僅供工程師學(xué)習(xí)之用,如有內(nèi)容侵權(quán)或者其他違規(guī)問(wèn)題,請(qǐng)聯(lián)系本站處理。 舉報(bào)投訴
  • 控制器
    +關(guān)注

    關(guān)注

    114

    文章

    16838

    瀏覽量

    182263
  • 嵌入式
    +關(guān)注

    關(guān)注

    5125

    文章

    19438

    瀏覽量

    313093
  • 數(shù)據(jù)通信
    +關(guān)注

    關(guān)注

    2

    文章

    454

    瀏覽量

    34213
  • Stu
    Stu
    +關(guān)注

    關(guān)注

    0

    文章

    2

    瀏覽量

    7344
  • JSON
    +關(guān)注

    關(guān)注

    0

    文章

    119

    瀏覽量

    7205

原文標(biāo)題:嵌入式實(shí)用知識(shí)之JSON數(shù)據(jù)

文章出處:【微信號(hào):玩點(diǎn)嵌入式,微信公眾號(hào):玩點(diǎn)嵌入式】歡迎添加關(guān)注!文章轉(zhuǎn)載請(qǐng)注明出處。

收藏 人收藏

    評(píng)論

    相關(guān)推薦

    基于stm32單片機(jī)的cjson庫(kù)c語(yǔ)言例程

    大家好,現(xiàn)在給大家提供一個(gè)基于stm32f030單片機(jī)的cjson庫(kù)c語(yǔ)言例程。json是在互聯(lián)網(wǎng)領(lǐng)域數(shù)據(jù)傳輸中較常用的協(xié)議,該協(xié)議比較輕量級(jí)也通俗易懂,在物聯(lián)網(wǎng)快速發(fā)展的時(shí)代,物物與平臺(tái)
    發(fā)表于 12-02 22:14

    LiteOS云端對(duì)接教程01-cJSON組件使用教程

    Notation,即 JS對(duì)象簡(jiǎn)譜,是一種輕量級(jí)的數(shù)據(jù)格式。它采用完全獨(dú)立于編程語(yǔ)言的文本格式來(lái)存儲(chǔ)和表示數(shù)據(jù),語(yǔ)法簡(jiǎn)潔、層次結(jié)構(gòu)清晰,易于人閱讀和編寫,同時(shí)也易于機(jī)器解析和生成,有
    發(fā)表于 02-26 09:53

    cJSON是什么?有何特點(diǎn)

    一、cJSON介紹cJSON是一個(gè)使用C語(yǔ)言編寫的JSON數(shù)據(jù)解析器,具有超輕便,可移植,單文件的特點(diǎn),使用MIT開源協(xié)議。cJSON的源碼
    發(fā)表于 01-12 08:22

    cjson庫(kù)解析數(shù)據(jù)

    最近項(xiàng)目用到cjson庫(kù)解析數(shù)據(jù),當(dāng)解析的的數(shù)據(jù)比較長(zhǎng)時(shí),會(huì)
    發(fā)表于 01-12 06:14

    單片機(jī)如果不用cJSON庫(kù)會(huì)怎樣呢

    /*處理網(wǎng)絡(luò)數(shù)據(jù)的時(shí)候往往需要用到JSON數(shù)據(jù)格式,單片機(jī)如果不用cJSON庫(kù),處理起來(lái)會(huì)非常吃力以下程序與注釋講解了cJSON在STM32
    發(fā)表于 02-21 07:31

    一文解讀基于RTThread使用libcs??v庫(kù)進(jìn)行數(shù)據(jù)解析

    1、rtthread運(yùn)行l(wèi)ibcs??v 庫(kù)的使用最近做一個(gè),需要做數(shù)據(jù)存儲(chǔ)化的。一開始是,使用數(shù)據(jù)生成的目標(biāo)文件格式為項(xiàng)目名稱,保存數(shù)據(jù)文件來(lái)
    發(fā)表于 08-25 15:40

    如何避免在解析cJSON時(shí)一個(gè)函數(shù)內(nèi)出現(xiàn)過(guò)多的if語(yǔ)句呢?

    ,說(shuō)明我們的cJSON格式的報(bào)文有很多的同級(jí)對(duì)象,不同的對(duì)象對(duì)應(yīng)不同的業(yè)務(wù),所以我們應(yīng)該以業(yè)務(wù)來(lái)進(jìn)行劃分,盡量將不同的數(shù)據(jù)解析劃分到對(duì)應(yīng)的業(yè)務(wù)代碼模塊中去。而不是全部都放在一塊,那樣自
    發(fā)表于 11-10 16:55

    在MQTT中的TCP樣例中,需要添加cjson解析代碼并將獲取到的數(shù)據(jù)輸出出去,應(yīng)該如何修改代碼?

    NULL! ");}// 解析數(shù)據(jù)// char bssid[23] = {0};pJsonRoot = cJSON_GetObjectItem(pJsonRoot, "
    發(fā)表于 02-10 08:38

    在MQTT中的TCP樣例中,如何添加cjson解析代碼并將獲取到的數(shù)據(jù)輸出出去?

    NULL! ");}// 解析數(shù)據(jù)// char bssid[23] = {0};pJsonRoot = cJSON_GetObjectItem(pJsonRoot, "
    發(fā)表于 03-03 06:24

    在MQTT中的TCP樣例中,如何添加cjson解析代碼并將獲取到的數(shù)據(jù)輸出出去?

    ;, event->data_len, event->data);// 創(chuàng)建json數(shù)據(jù)解析對(duì)象pJsonRoot = cJSON_Parse(event->
    發(fā)表于 03-08 06:28

    RT-Thread使用cjson軟件發(fā)送64位長(zhǎng)整型數(shù)據(jù)

      開發(fā)環(huán)境:野火的stm32f407,rt-thread studio版本是版本: 2.2.6,stm32f4的資源為0.2.2,rt-thread版本為4.1.1,cjson軟件使用的版本
    發(fā)表于 03-13 15:54

    用Delphi數(shù)據(jù)庫(kù)開發(fā)

    用Delphi數(shù)據(jù)庫(kù)開發(fā):實(shí)驗(yàn)三 用Delphi數(shù)據(jù)庫(kù)開發(fā)一、實(shí)驗(yàn)?zāi)康耐ㄟ^(guò)使用Delphi中BDE連接SQL數(shù)據(jù)庫(kù),掌握Delphi環(huán)境
    發(fā)表于 05-10 11:05 ?44次下載

    STM32F103C8T6移植cJSON解析JSON數(shù)據(jù)包

    /*處理網(wǎng)絡(luò)數(shù)據(jù)的時(shí)候往往需要用到JSON數(shù)據(jù)格式,單片機(jī)如果不用cJSON庫(kù),處理起來(lái)會(huì)非常吃力以下程序與注釋講解了cJSON在STM32
    發(fā)表于 12-27 18:29 ?27次下載
    STM32F103C8T6移植<b class='flag-5'>cJSON</b><b class='flag-5'>解析</b>JSON<b class='flag-5'>數(shù)據(jù)包</b>

    Oracle數(shù)據(jù)庫(kù)ASM磁盤掉線的數(shù)據(jù)恢復(fù)案例

    數(shù)據(jù)庫(kù)故障: Oracle數(shù)據(jù)庫(kù)的ASM磁盤掉線,ASM實(shí)例不能掛載。管理員嘗試修復(fù)數(shù)據(jù)庫(kù)但是沒有成功。 數(shù)據(jù)庫(kù)
    的頭像 發(fā)表于 03-03 13:42 ?1245次閱讀
    Oracle<b class='flag-5'>數(shù)據(jù)庫(kù)</b>ASM磁盤<b class='flag-5'>組</b>掉線的<b class='flag-5'>數(shù)據(jù)</b>恢復(fù)案例

    RT-Thread使用cjson軟件發(fā)送64位長(zhǎng)整型數(shù)據(jù)

    開發(fā)環(huán)境:野火的stm32f407,rt-thread studio版本是版本: 2.2.6,stm32f4的資源為0.2.2,rt-thread版本為4.1.1,cjson軟件使用的版本是latest。
    的頭像 發(fā)表于 10-11 15:09 ?1188次閱讀
    RT-Thread使用<b class='flag-5'>cjson</b>軟件<b class='flag-5'>包</b>發(fā)送64位長(zhǎng)整型<b class='flag-5'>數(shù)據(jù)</b>