0

0

c++中如何解析json数据_c++常用json库的使用方法对比【详解】

裘德小鎮的故事

裘德小鎮的故事

发布时间:2026-01-23 17:55:19

|

450人浏览过

|

来源于php中文网

原创

jsoncpp是CMake项目中最稳妥的JSON解析方案;需检查parse()返回值、用isMember()防越界、数字统一用asDouble()/asInt()、确保UTF-8编码。

c++中如何解析json数据_c++常用json库的使用方法对比【详解】

jsoncpp 解析 JSON 字符串最稳妥

如果你的项目已用 CMake 管理,且不强求零依赖或极致性能,jsoncpp 是目前最省心的选择。它语法直观、文档完整、错误提示清晰,对嵌套对象/数组、空值、转义字符支持稳定。

常见错误现象:Json::Value root; 直接访问未解析的 root["key"] 会返回空对象而非报错;若 JSON 格式非法(如多逗号、单引号),parseFromStream 默认静默失败,需检查 parser.parse() 返回值。

  • 必须先调用 parser.parse(json_string, root, &errors),再判断返回值是否为 true
  • 读取字段前用 root.isMember("field") 防止越界
  • 数字类型统一用 asDouble()asInt(),避免隐式转换出错
  • 中文字符串需确保输入是 UTF-8 编码jsoncpp 不做编码转换
Json::CharReaderBuilder builder;
std::string errors;
std::istringstream json_stream(R"({"name":"张三","age":28,"tags":["cpp","json"]})");
Json::Value root;
if (!Json::parseFromStream(builder, json_stream, &root, &errors)) {
    std::cerr << "Parse error: " << errors << std::endl;
    return;
}
std::string name = root["name"].asString();
int age = root["age"].asInt();
for (const auto& tag : root["tags"]) {
    std::cout << tag.asString() << std::endl;
}

nlohmann/json 写法最接近现代 C++ 习惯

头文件即用、无需编译依赖、支持结构体自动映射(JSON_FOR_EACH_NESTED 或自定义 to_json/from_json),适合新项目或快速原型。但要注意:它把 JSON 当作一等公民,所有操作都基于 json 类型,原生不支持直接读取 char*,必须先构造 json j = json::parse(str)

容易踩的坑:j["missing_key"] 会自动创建空值(不是 nullptr),导致误判存在性;j.at("key") 才抛异常;迭代 JSON 对象时,j.items() 返回的是 std::pair<:string json>,不是传统 map 迭代器。

立即学习C++免费学习笔记(深入)”;

Android数据格式解析对象JSON用法 WORD版
Android数据格式解析对象JSON用法 WORD版

本文档主要讲述的是Android数据格式解析对象JSON用法;JSON可以将Java对象转成json格式的字符串,可以将json字符串转换成Java。比XML更轻量级,Json使用起来比较轻便和简单。JSON数据格式,在Android中被广泛运用于客户端和服务器通信,在网络数据传输与解析时非常方便。希望本文档会给有需要的朋友带来帮助;感兴趣的朋友可以过来看看

下载
  • j.at("key") 替代 j["key"] 做安全访问
  • 解析失败默认抛 json::parse_error 异常,建议用 try/catch 包裹
  • 写入文件时注意 j.dump(2) 的缩进参数是可选的,不传则无格式化
  • 不支持部分老旧编译器(如 GCC 4.8 以下、MSVC 2015 Update 2 以前)
#include 
using json = nlohmann::json;
std::string s = R"({"city":"北京","population":2171})";
try {
    json j = json::parse(s);
    std::string city = j.at("city").get();
    int pop = j.at("population").get();
} catch (json::parse_error& e) {
    std::cerr << "JSON parse error at byte " << e.byte << std::endl;
}

rapidjson 性能高但 API 设计反直觉

在嵌入式或高频解析场景(如日志预处理、游戏协议解析)中,rapidjson 解析速度通常比 jsoncpp 快 2–3 倍,内存占用更低。但它采用 SAX(事件驱动)和 DOM(树形)双模式,初学者容易混淆 DocumentValue 的生命周期,且错误码分散(kParseErrorNone 等宏需手动查)。

典型问题:用 document.Parse() 后直接 document["key"] 报错,因为没检查 document.IsObject()Value 是非持有型引用,不能脱离 Document 单独存在;字符串字面量要用 GetString(),不能直接赋给 std::string

  • 每次解析后必须调用 document.HasParseError() == false 判断成功
  • 访问前确认类型:用 value.IsString()value.IsArray() 等,而非仅靠字段名
  • 获取字符串必须用 value.GetString(),且其返回指针依赖 Document 生命周期
  • 启用 RAPIDJSON_HAS_STDSTRING 宏才能用 std::string 构造器
#define RAPIDJSON_HAS_STDSTRING 1
#include 
#include 
#include 
rapidjson::Document document;
if (document.Parse(R"({"score":95.5,"passed":true})").HasParseError()) {
    std::cerr << "Offset " << document.GetErrorOffset() << std::endl;
    return;
}
double score = document["score"].GetDouble();
bool passed = document["passed"].GetBool();

选库前必须核对这三点

很多项目卡在选型上,其实只需明确三个事实:

  • 是否允许运行时抛异常?nlohmann/json 默认抛,jsoncpprapidjson 用返回值/状态码
  • 是否要跨平台静态链接?jsoncpp 需编译,nlohmann/json 头文件即用,rapidjson 同样头文件但模板深度大,可能拖慢编译
  • 是否需 schema 校验或注释支持?三者均不原生支持,得额外引入 json-schema-validator 或自行实现

真正难的不是语法,而是当 JSON 来源不可控(比如用户上传、第三方接口)、字段类型不一致(有时是 "123",有时是 123)、含 BOM 或混合编码时,怎么让解析逻辑不崩——这得靠前置清洗 + 类型断言 + fallback 策略,而不是换一个库就能解决。

相关专题

更多
json数据格式
json数据格式

JSON是一种轻量级的数据交换格式。本专题为大家带来json数据格式相关文章,帮助大家解决问题。

417

2023.08.07

json是什么
json是什么

JSON是一种轻量级的数据交换格式,具有简洁、易读、跨平台和语言的特点,JSON数据是通过键值对的方式进行组织,其中键是字符串,值可以是字符串、数值、布尔值、数组、对象或者null,在Web开发、数据交换和配置文件等方面得到广泛应用。本专题为大家提供json相关的文章、下载、课程内容,供大家免费下载体验。

533

2023.08.23

jquery怎么操作json
jquery怎么操作json

操作的方法有:1、“$.parseJSON(jsonString)”2、“$.getJSON(url, data, success)”;3、“$.each(obj, callback)”;4、“$.ajax()”。更多jquery怎么操作json的详细内容,可以访问本专题下面的文章。

310

2023.10.13

go语言处理json数据方法
go语言处理json数据方法

本专题整合了go语言中处理json数据方法,阅读专题下面的文章了解更多详细内容。

76

2025.09.10

string转int
string转int

在编程中,我们经常会遇到需要将字符串(str)转换为整数(int)的情况。这可能是因为我们需要对字符串进行数值计算,或者需要将用户输入的字符串转换为整数进行处理。php中文网给大家带来了相关的教程以及文章,欢迎大家前来学习阅读。

358

2023.08.02

js 字符串转数组
js 字符串转数组

js字符串转数组的方法:1、使用“split()”方法;2、使用“Array.from()”方法;3、使用for循环遍历;4、使用“Array.split()”方法。本专题为大家提供js字符串转数组的相关的文章、下载、课程内容,供大家免费下载体验。

278

2023.08.03

js截取字符串的方法
js截取字符串的方法

js截取字符串的方法有substring()方法、substr()方法、slice()方法、split()方法和slice()方法。本专题为大家提供字符串相关的文章、下载、课程内容,供大家免费下载体验。

212

2023.09.04

java基础知识汇总
java基础知识汇总

java基础知识有Java的历史和特点、Java的开发环境、Java的基本数据类型、变量和常量、运算符和表达式、控制语句、数组和字符串等等知识点。想要知道更多关于java基础知识的朋友,请阅读本专题下面的的有关文章,欢迎大家来php中文网学习。

1491

2023.10.24

C++ 高级模板编程与元编程
C++ 高级模板编程与元编程

本专题深入讲解 C++ 中的高级模板编程与元编程技术,涵盖模板特化、SFINAE、模板递归、类型萃取、编译时常量与计算、C++17 的折叠表达式与变长模板参数等。通过多个实际示例,帮助开发者掌握 如何利用 C++ 模板机制编写高效、可扩展的通用代码,并提升代码的灵活性与性能。

10

2026.01.23

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
WEB前端教程【HTML5+CSS3+JS】
WEB前端教程【HTML5+CSS3+JS】

共101课时 | 8.5万人学习

JS进阶与BootStrap学习
JS进阶与BootStrap学习

共39课时 | 3.2万人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号