C语言的JSON库

cJSON库下载地址 https://github.com/DaveGamble/cJSON

c语言JSON库比较多,这里就讲其中一种叫cJSON的库,所有的库使用大同小异,有兴趣的同学们请自行研究。如果学习了C++,其实会发现支持面向对象的语言在解析JSON的时候更加形象。

cJSON库在使用的时候只需要如下两步:

  • 将cJSON.c(或者库文件) 和 cJSON.h添加到项目中即可

  • 如果在命令行中进行链接 还需要加上-lm 表示链接math库

C语言函数库写JSON文件

从缓冲区中解析出JSON结构

/* Supply a block of JSON, and this returns a cJSON object you can interrogate. Call cJSON_Delete when finished. 解析一块JSON数据返回cJSON结构,在使用完之后调用cJSON_Delete函数释放json对象结构*/
extern cJSON *cJSON_Parse(const char *value);

将传入的JSON结构转化为字符串

/* Render a cJSON entity to text for transfer/storage. Free the char* when finished. */
extern char  *cJSON_Print(cJSON *item);
(可用于输出到输出设备),使用完之后free(char *);

将JSON结构所占用的数据空间释放

/* Delete a cJSON structure. */
void cJSON_Delete(cJSON *c)

练习1: 将字符串 char *char_json = "{\"habit\":\"lol\"}";解析为json保存为0001.json

这里只说明主要库函数,其他库函数基本类似。请直接查看cJSON.h文件。

主要库函数:

创建函数返回创建的json结构

创建一个值类型的数据

extern cJSON *cJSON_CreateNumber(double num);
extern cJSON *cJSON_CreateString(const char *string);
extern cJSON *cJSON_CreateArray(void);

创建一个对象(文档)

extern cJSON *cJSON_CreateObject(void);

数组创建以及添加

cJSON *cJSON_CreateIntArray(const int *numbers,int count);
void cJSON_AddItemToArray(cJSON *array, cJSON *item);

JSON嵌套

【向对象中增加键值对】cJSON_AddItemToObject(root, "rows", 值类型数据相关函数());
【向对象中增加数组】cJSON_AddItemToObject(root, "rows", cJSON_CreateArray());
【向数组中增加对象】cJSON_AddItemToArray(rows, cJSON_CreateObject());

几个能提高操作效率的宏函数

#define cJSON_AddNumberToObject(object,name,n)    \
            cJSON_AddItemToObject(object, name,cJSON_CreateNumber(n))
#define cJSON_AddStringToObject(object,name,s)\
            cJSON_AddItemToObject(object, name, cJSON_CreateString(s))

练习2 使用上述库函数创建一个如下的json文件,名字为02.json

{
    "country":"china","stars":
        [
            {"name":"Faye","address":"beijing"},
            {"name":"andy","address":"HK"},
            {"name":"eddie","address":"Taiwan"}
        ]
}

C语言库函数解析JSON文件

主要库函数:针对每个函数做一个示例代码演示调用

/* Get item "string" from object. Case insensitive. 根据键找json结点 */
extern cJSON *cJSON_GetObjectItem(cJSON *object,const char *string);


/*判断是否有key是string的项 如果有返回1 否则返回0*/
extern int cJSON_HasObjectItem(cJSON *object,const char *string)
{    return cJSON_GetObjectItem(object,string)?1:0;    }


/* Returns the number of items in an array (or object). 返回数组结点array中成员的个数(数组大小) */
extern int      cJSON_GetArraySize(cJSON *array);


/* Retrieve item number "item" from array "array". Returns NULL if unsuccessful.
   根据数组下标index取array数组结点的第index个成员 返回该成员节点
*/
extern cJSON *cJSON_GetArrayItem(cJSON *array,int index);

/* Macro for iterating over an array  遍历数组*/
#define cJSON_ArrayForEach(pos, head)    for(pos = (head)->child; pos != NULL; pos = pos->next)

物流接口/快递接口:
http://www.kuaidi100.com/query?type=快递公司代号&postid=快递单号
ps:快递公司编码:申通="shentong" EMS="ems" 顺丰="shunfeng" 圆通="yuantong" 中通="zhongtong" 韵达="yunda" 天天="tiantian" 汇通="huitongkuaidi" 全峰="quanfengkuaidi" 德邦="debangwuliu" 宅急送="zhaijisong"

解析练习 获取并显示快递编号nu;然后取出data中的每条信息并且予以显示

显示结果如下
mo@test-pc JSON/json03
$ ls
01_json.c                            cJSON.c         json01.pro.user
02_json.c                            cJSON.h         main.exe
03_express_information.json          deployment.pri  main.exe.backup
03_json_parse_express_information.c  json01.pro

mo@test-pc JSON/json03
$ gcc -o main 03_json_parse_express_information.c  cJSON.c
mo@test-pc JSON/json03

$ ./main.exe
express info[nu] is 768433135999

time:2016-04-10 13:17:42
info:北京北苑的派件已签收,感谢您使用中通快递!

time:2016-04-10 07:36:05
info:北京北苑 的 刘肖18010456227 正在派件

time:2016-04-10 06:34:32
info:快件已到达 北京北苑 上一站是 北京

time:2016-04-09 21:14:21
info:快件离开 北京市内部 已发往 北京北苑

time:2016-04-09 13:30:52
info:快件已到达 北京 上一站是 0

time:2016-04-08 01:10:48
info:快件离开 广州中心 已发往 110000

time:2016-04-07 10:16:54
info:快件已到达 广州中心 上一站是 0

time:2016-04-07 05:59:11
info:快件离开 深圳中心 已发往 440000

time:2016-04-07 01:10:43
info:快件已到达 深圳中心 上一站是 深圳华侨城

time:2016-04-06 20:17:06
info:快件离开 深圳华侨城 已发往 深圳中心

time:2016-04-06 18:23:45
info:深圳华侨城 的 邹国 已收件