在C语言中如何获取JSON串中的某个值
在C语言中处理JSON数据通常需要借助第三方库,因为C语言本身没有内置的JSON解析功能,本文将介绍几种常用的C语言JSON库,并详细讲解如何使用它们从JSON串中获取特定的值。
常用的C语言JSON库
- cJSON:轻量级、单文件的JSON解析器,使用简单,适合嵌入式系统。
- Jansson:功能丰富,支持JSON的生成、解析和查询,API设计合理。
- yajl:高性能的JSON解析器,支持流式解析。
- ujson:专注于速度的JSON解析库。
本文将以最常用的cJSON为例,讲解如何获取JSON串中的某个值。
使用cJSON获取JSON值
安装和引入cJSON
如果使用cJSON,首先需要下载其源代码(https://github.com/DaveGamble/cJSON),然后将其中的cJSON.h和cJSON.c添加到你的项目中。
#include "cJSON.h"
解析JSON字符串
假设我们有以下JSON字符串:
{
"name": "John",
"age": 30,
"isStudent": false,
"address": {
"street": "123 Main St",
"city": "New York"
},
"hobbies": ["reading", "swimming", "coding"]
}
获取简单值
// 解析JSON字符串
char *json_string = "{\"name\":\"John\",\"age\":30,\"isStudent\":false,\"address\":{\"street\":\"123 Main St\",\"city\":\"New York\"},\"hobbies\":[\"reading\",\"swimming\",\"coding\"]}";
cJSON *root = cJSON_Parse(json_string);
if (root == NULL) {
const char *error_ptr = cJSON_GetErrorPtr();
if (error_ptr != NULL) {
fprintf(stderr, "Error before: %s\n", error_ptr);
}
return 1;
}
// 获取字符串值
cJSON *name = cJSON_GetObjectItemCaseSensitive(root, "name");
if (cJSON_IsString(name) && (name->valuestring != NULL)) {
printf("Name: %s\n", name->valuestring);
}
// 获取数字值
cJSON *age = cJSON_GetObjectItemCaseSensitive(root, "age");
if (cJSON_IsNumber(age)) {
printf("Age: %d\n", age->valueint);
}
// 获取布尔值
cJSON *isStudent = cJSON_GetObjectItemCaseSensitive(root, "isStudent");
if (cJSON_IsBool(isStudent)) {
printf("Is student: %s\n", cJSON_IsTrue(isStudent) ? "true" : "false");
}
// 释放JSON对象
cJSON_Delete(root);
获取嵌套对象的值
// 获取嵌套对象
cJSON *address = cJSON_GetObjectItemCaseSensitive(root, "address");
if (cJSON_IsObject(address)) {
cJSON *street = cJSON_GetObjectItemCaseSensitive(address, "street");
if (cJSON_IsString(street) && (street->valuestring != NULL)) {
printf("Street: %s\n", street->valuestring);
}
cJSON *city = cJSON_GetObjectItemCaseSensitive(address, "city");
if (cJSON_IsString(city) && (city->valuestring != NULL)) {
printf("City: %s\n", city->valuestring);
}
}
获取数组中的值
// 获取数组
cJSON *hobbies = cJSON_GetObjectItemCaseSensitive(root, "hobbies");
if (cJSON_IsArray(hobbies)) {
int hobby_count = cJSON_GetArraySize(hobbies);
printf("Hobbies (%d): ", hobby_count);
for (int i = 0; i < hobby_count; i++) {
cJSON *hobby = cJSON_GetArrayItem(hobbies, i);
if (cJSON_IsString(hobby) && (hobby->valuestring != NULL)) {
printf("%s ", hobby->valuestring);
}
}
printf("\n");
}
使用Jansson获取JSON值
如果选择使用Jansson,其API略有不同:
#include <jansson.h>
// 解析JSON字符串
json_error_t error;
json_t *root = json_loads(json_string, 0, &error);
if (!root) {
fprintf(stderr, "JSON error on line %d: %s\n", error.line, error.text);
return 1;
}
// 获取字符串值
json_t *name = json_object_get(root, "name");
if (json_is_string(name)) {
printf("Name: %s\n", json_string_value(name));
}
// 获取数字值
json_t *age = json_object_get(root, "age");
if (json_is_integer(age)) {
printf("Age: %d\n", json_integer_value(age));
}
// 释放JSON对象
json_decref(root);
错误处理和注意事项
- 检查返回值:始终检查JSON解析函数的返回值,确保解析成功。
- 释放内存:使用完JSON对象后,记得调用相应的释放函数(如
cJSON_Delete或json_decref),避免内存泄漏。 - 类型检查:在访问JSON值之前,使用
cJSON_IsString、cJSON_IsNumber等函数检查值的类型。 - 大小写敏感:
cJSON_GetObjectItemCaseSensitive是区分大小写的,而cJSON_GetObjectItem不区分大小写。
在C语言中处理JSON数据需要借助第三方库,cJSON和Jansson是两个常用的选择,通过理解这些库的基本API,你可以轻松地从JSON字符串中提取所需的值,关键在于正确解析JSON、检查值的类型、安全地访问数据,并在使用后妥善释放内存,希望本文能帮助你在C语言项目中有效地处理JSON数据。



还没有评论,来说两句吧...