使用cJSON解析JSON字符串数组未获正确输出,求代码修改方案
解决cJSON解析JSON字符串数组无输出问题
问题背景
使用cJSON库解析JSON时,无法输出Localization节点下EN字符串数组的内容,目标字符串未在输出窗口显示,故障代码位于//访问JSON数据注释下方。
目标JSON结构
{ "GameName": "Plants vs. Zombies", "GameProcessName":"Plants vs. Zombies", "ModifiableItem":"2", "BaseAddressTable":[ { "0x24056588":"99999", "ModificationType":"" }, { "BaseAddressValue":"", "ModificationType":"" } ], "id":["PZ01","PZ02"], "BaseAddressName":["0x24056588",""], "Localization":{ "CN":["无限阳光","无限金币"], "EN":["Infinite sunshine","Infinite"] } }
原代码问题分析
- 变量重复定义:同时声明
char *str_tmp;和cJSON *str_tmp;,编译报错导致逻辑异常 - 节点引用错误:将Localization节点赋值给
array变量,但后续使用未初始化的Localization野指针获取EN节点 - 数组处理逻辑错误:EN是字符串数组,直接取
valuestring会返回NULL,且判断逻辑颠倒(NULL时才执行打印,实际应遍历数组) - 文件读取未加终止符:
fread读取后未给buffer添加\0,cJSON解析可能失败 - 错误处理不完整:文件打开失败后未终止函数,后续操作会触发崩溃
修正后的代码
void FileReading(char *p) { char* TableFilePath = p; // 传入的Table.json路径 char* GameName; // 打开JSON文件 FILE *fp = fopen(TableFilePath, "r"); if (fp == NULL) { // 文件未找到 HANDLE hConsole = GetStdHandle(STD_OUTPUT_HANDLE); SetConsoleTextAttribute(hConsole, 0xc); // 设置红色字体 printf("文件打开失败\n"); system("pause"); return; // 终止函数,避免后续错误 } // 读取文件内容到字符串 char buffer[1024] = {0}; // 初始化buffer,避免垃圾数据 int len = fread(buffer, 1, sizeof(buffer)-1, fp); // 留一个位置放终止符 buffer[len] = '\0'; // 添加字符串终止符,确保cJSON能正确解析 fclose(fp); // 解析JSON数据 cJSON *json = cJSON_Parse(buffer); if (json == NULL) { const char *error_ptr = cJSON_GetErrorPtr(); if (error_ptr != NULL) { HANDLE hConsole = GetStdHandle(STD_OUTPUT_HANDLE); SetConsoleTextAttribute(hConsole, 0xc); // 红色 printf("JSON解析错误: %s\n", error_ptr); system("pause"); } cJSON_Delete(json); return; } // 访问JSON数据:获取Localization下的EN字符串数组 cJSON *Localization = cJSON_GetObjectItem(json, "Localization"); if (Localization == NULL) { printf("未找到Localization节点\n"); cJSON_Delete(json); return; } cJSON *EN_array = cJSON_GetObjectItem(Localization, "EN"); if (EN_array == NULL || !cJSON_IsArray(EN_array)) { printf("未找到有效的EN数组\n"); cJSON_Delete(json); return; } // 遍历EN数组并输出内容 int array_size = cJSON_GetArraySize(EN_array); printf("EN数组内容:\n"); for (int i = 0; i < array_size; i++) { cJSON *item = cJSON_GetArrayItem(EN_array, i); if (cJSON_IsString(item)) { printf("- %s\n", item->valuestring); } } // 释放cJSON内存 cJSON_Delete(json); }
修正说明
- 修复变量重复定义问题,统一用cJSON类型指针处理节点
- 正确获取Localization和EN数组节点,添加空指针与类型校验
- 遍历EN数组时判断元素类型,确保输出有效字符串
- 给文件读取的buffer添加终止符,修复解析失败隐患
- 完善错误处理逻辑,避免空指针访问与程序崩溃
内容的提问来源于stack exchange,提问作者HAF
相关产品推荐
相关产品推荐

