回答

收藏

[评测分享] 【米尔-MYD-LR3568-GK开发板--试用评测】17——处理Json

#板卡评测 #板卡评测 1436 人阅读 | 0 人回复 | 2024-11-29

本帖最后由 stm1024 于 2024-11-29 22:53 编辑

JSON(JavaScript Object Notation,JavaScript对象表示法)是基于ECMAScript的一个子集设计的,是一种开放标准的文件格式和数据交换格式,它易于人阅读和编写,同时也易于机器解析和生成。JSON独立于语言设计,很多编程语言都支持JSON格式的数据交换。JSON是一种常用的数据格式,在电子数据交换中有多种用途,包括与服务器之间的Web应用程序的数据交换。其简洁和清晰的层次结构有效地提升了网络传输效率,使其成为理想的数据交换语言。其文件通常使用扩展名.json。
本次测试使用C语言处理Json文件。
1. 使用到的库
推荐使用cJson库,?cJson?是一个轻量级的JSON解析库,主要用于C语言环境中处理JSON数据。它提供了一系列函数来创建、解析、修改和序列化JSON对象。cJson的基本功能
?创建JSON对象?:可以使用cJSON_CreateObject、cJSON_CreateArray等函数创建JSON对象和数组。
?添加元素?:可以通过cJSON_AddItemToObject、cJSON_AddItemToArray等函数向JSON对象或数组中添加元素。
?解析JSON字符串?:使用cJSON_Parse函数可以将JSON格式的字符串解析为cJson结构体表示的对象。
?生成JSON字符串?:通过cJSON_Print函数可以将cJson结构体表示的对象转换为JSON格式的字符串。
cJson的使用场景
?数据交换?:在C语言编写的应用程序之间进行数据交换时,cJson可以方便地将数据序列化为JSON格式,便于传输和存储。
?配置文件?:用于读取和写入配置文件,将复杂的配置信息以JSON格式存储和读取。
?网络通信?:在网络通信中,cJson可以将结构化数据转换为JSON格式,便于通过HTTP等协议传输。
cJson的优缺点
?优点?:
?轻量级?:cJson的实现较为简单,占用内存少,适合嵌入式系统和资源有限的设备。
?易用性?:提供了丰富的API,易于使用和理解。
?跨平台?:由于是C语言编写,可以在多种平台上使用。
?缺点?:
?性能?:相对于一些高性能的JSON处理库,cJson在处理大量数据时可能效率较低。
?功能限制?:虽然提供了基本的JSON处理功能,但对于一些特殊需求可能需要其他库的支持。

2. 写Json文件
如果我们需要将数据以Json方式传递,则可以通过写文件的方式生成Json文件,实现代码如下:
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <string.h>
  4. #include "cJSON.h"

  5. int main(int argc, const char *argv[])
  6. {
  7.     if (argc < 2)
  8.     {
  9.         printf("Usage: %s filename\n", argv[0]);
  10.         return 1;
  11.     }
  12.     cJSON *root = cJSON_CreateObject();
  13.     double ds[] = {65.6, 33.4, 95.6, 87.8};
  14.     char *jstr = NULL;
  15.     int i;
  16.     cJSON_AddStringToObject(root, "name", "Bob");

  17.     // add an array of strings
  18.     cJSON *hobby = cJSON_CreateArray();
  19.     cJSON_AddItemToArray(hobby, cJSON_CreateString("basketball"));
  20.     cJSON_AddItemToArray(hobby, cJSON_CreateString("football"));
  21.     cJSON_AddItemToArray(hobby, cJSON_CreateString("swim"));
  22.     cJSON_AddItemToObject(root, "hobby", hobby);
  23.     // add an array of doubles
  24.    
  25.     //method 1:
  26.     cJSON* score = cJSON_CreateDoubleArray(ds,sizeof(ds)/sizeof(double));
  27.     cJSON_AddItemToObject(root, "score", score);
  28.    
  29.     /*
  30.     // method 2:
  31.     cJSON *score = cJSON_CreateArray();
  32.     for (i = 0; i < sizeof(ds) / sizeof(double); i++)
  33.         cJSON_AddItemToArray(score, cJSON_CreateNumber(ds[i]));
  34.     cJSON_AddItemToObject(root, "score", score);
  35.     */

  36.     // print Json string
  37.     jstr = cJSON_Print(root);
  38.     printf("%s\n", jstr);
  39.     FILE* fp=fopen(argv[1],"w");
  40.     fwrite(jstr,sizeof(char),strlen(jstr),fp);
  41.     fclose(fp);
  42.     free(jstr); // remember to free it
  43.     cJSON_Delete(root);
  44.     return 0;
  45. }
复制代码
在开发板上使用gcc编译:
  1. gcc -g cJSON.c cjw.c -lm -o cjw
复制代码
运行效果如下:

可以看到在同名文件夹下生成了一个名为hello.json的文件:

3. 读Json文件
读取Json文件或者Json字符串是一样的效果,实现起来也很简单,代码如下:
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <string.h>
  4. #include "cJSON.h"

  5. //read json file and parse it into a cJSON object
  6. cJSON *parse_json_file(const char *filename)
  7. {
  8.     FILE *fp = fopen(filename, "rb");
  9.     if (fp == NULL) {
  10.         printf("Failed to open file %s\n", filename);
  11.         return NULL;
  12.     }
  13.     fseek(fp, 0, SEEK_END);
  14.     long size = ftell(fp);
  15.     fseek(fp, 0, SEEK_SET);
  16.     char *json_str = (char *)malloc(size + 1);
  17.     fread(json_str, 1, size, fp);
  18.     json_str[size] = '\0';
  19.     fclose(fp);
  20.     cJSON *json = cJSON_Parse(json_str);
  21.     free(json_str);
  22.     return json;
  23. }

  24. //print cJSON object in a formatted way
  25. void print_json(cJSON *json)
  26. {
  27.     char *str = cJSON_Print(json);
  28.     printf("%s\n", str);
  29.     free(str);
  30. }

  31. //example usage of the above functions
  32. int main(int argc, char **argv)
  33. {
  34.     if (argc < 2)
  35.     {
  36.         printf("Usage: %s filename\n", argv[0]);
  37.         return 1;
  38.     }
  39.     cJSON *json = parse_json_file(argv[1]);
  40.     if (json == NULL)
  41.         return 1;
  42.    
  43.     print_json(json);
  44.    
  45.     //get the value of a key in the json object
  46.     cJSON *name = cJSON_GetObjectItem(json, "name");
  47.     if (name != NULL && name->type == cJSON_String)
  48.         printf("Name: %s\n", name->valuestring);
  49.    
  50.     //get the value of an array element
  51.     cJSON *array = cJSON_GetObjectItem(json, "score");
  52.     if (array != NULL && array->type == cJSON_Array)
  53.     {
  54.         int i;
  55.         for (i = 0; i < cJSON_GetArraySize(array); i++)
  56.         {
  57.             cJSON *element = cJSON_GetArrayItem(array, i);
  58.             if (element != NULL && element->type == cJSON_Number)
  59.                 printf("Element %d: %f\n", i, element->valuedouble);
  60.         }
  61.     }

  62.     cJSON_Delete(json);
  63.     return 0;
  64. }
复制代码

同样使用开发板上的gcc编译一下,运行效果如下:

代码中第一部分是直接解析了字符串并打印,第二部分是读取了名称和score部分的值,可见解析正确。
对于嵌套的Json对象,当然也可以实现递归的解析函数,这里就不展开介绍了。此外,如果使用python的话,还会更加方便,但是运行速度感人。


分享到:
回复

使用道具 举报

您需要登录后才可以回帖 注册/登录

本版积分规则

5300 积分
55 主题
+ 关注
热门推荐
关闭

站长推荐上一条 /3 下一条