0

0

C++如何实现一个简单的JSON解析器?C++递归下降解析法实战【项目练习】

穿越時空

穿越時空

发布时间:2025-12-14 20:45:08

|

766人浏览过

|

来源于php中文网

原创

用C++11手写轻量级JSON解析器需采用递归下降法,为value、object、array等非终结符实现对应函数,配合JsonValue联合体结构和位置指针pos遍历字符串,正确处理转义、数字解析、空白跳过及错误定位。

c++如何实现一个简单的json解析器?c++递归下降解析法实战【项目练习】

用C++手写一个轻量级JSON解析器,核心是递归下降(Recursive Descent)——它天然契合JSON的嵌套结构(对象、数组可无限嵌套),逻辑清晰、易于理解和调试。不需要第三方库,纯标准C++11即可实现基础功能(字符串、数字、布尔、null、对象、数组)。

理解JSON语法与递归下降映射关系

JSON文本本质是上下文无关文法(CFG),递归下降就是为每个非终结符(如 valueobjectarray)写一个对应函数,函数内部按语法规则“向下”调用其他函数,形成自然的递归调用链。

关键文法规则(简化版):

  • valuestring | number | object | array | true | false | null
  • object{ [ member ( , member )* ] }
  • memberstring : value
  • array[ [ value ( , value )* ] ]

每个规则直接对应一个解析函数,比如 parse_value() 调用 parse_object()parse_array(),后者再递归调用 parse_value() —— 这就是“下降”和“递归”的由来。

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

设计核心数据结构:JsonValue

先定义一个能容纳所有JSON类型的联合体式容器(用 std::variant 或手动管理):

Frase
Frase

Frase是一款出色的长篇 AI 写作工具,快速创建seo优化的内容。

下载
struct JsonValue {
    enum Type { STRING, NUMBER, OBJECT, ARRAY, BOOL, NULL_T };
    Type type;
    std::string str;           // for STRING
    double num;                // for NUMBER
    bool boolean;              // for BOOL
    std::map obj;   // for OBJECT
    std::vector arr;             // for ARRAY
};

注意:NULL_T 可用特殊标记(如 num = NAN)或额外 bool is_null 字段;实际项目中推荐用 std::optionalstd::variant<:monostate ...> 更安全。

实现解析器骨架与关键函数

维护一个位置指针 pos 遍历输入字符串,跳过空白,按首字符分发:

  • 遇到 " → 调用 parse_string()(需处理转义,如 \"\\\n
  • 遇到 { → 调用 parse_object()(读 {,循环解析 "key": value,直到 }
  • 遇到 [ → 调用 parse_array()(读 [,循环解析 value,直到 ]
  • 遇到 t / f / n → 分别识别 truefalsenull
  • 遇到数字或负号 → 调用 parse_number()(支持整数、小数、科学计数法,可用 std::stod 或手动解析)

所有函数都接受并更新引用参数 size_t& pos,失败时抛异常或返回 std::nullopt(建议用异常,便于定位错误位置)。

实战要点与易错提醒

递归下降不是“写完就跑”,几个关键细节决定成败:

  • 跳空白必须统一:写一个 skip_whitespace(const std::string& s, size_t& pos),所有解析函数开头必调用
  • 字符串解析要小心:逐字符读,遇 " 结束;中间遇 \ 就取下一个字符,按规则转义(\\\, \"", \n→换行符等)
  • 数字解析别依赖 atof:它不检查非法尾部(如 "123abc" 会成功解析为123),应手动扫描合法数字字符后截取子串再转换
  • 错误提示要带位置:抛异常时附上 pos,比如 throw std::runtime_error("Expected ',' or '}' at " + std::to_string(pos));
  • 避免深递归爆:JSON嵌套过深(>1000层)可能栈溢出,生产环境需加深度限制(传入 max_depth 参数)

基本上就这些。写完后用典型用例测试:{"name":"Alice","scores":[95,87],"active":true}、空对象 {}、嵌套 {"a":{"b":[1,2]}}、非法输入(缺引号、逗号错位)看是否报错准确。不复杂但容易忽略边界,多测几遍就稳了。

相关专题

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

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

412

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数据方法,阅读专题下面的文章了解更多详细内容。

75

2025.09.10

string转int
string转int

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

318

2023.08.02

c语言中null和NULL的区别
c语言中null和NULL的区别

c语言中null和NULL的区别是:null是C语言中的一个宏定义,通常用来表示一个空指针,可以用于初始化指针变量,或者在条件语句中判断指针是否为空;NULL是C语言中的一个预定义常量,通常用来表示一个空值,用于表示一个空的指针、空的指针数组或者空的结构体指针。

232

2023.09.22

java中null的用法
java中null的用法

在Java中,null表示一个引用类型的变量不指向任何对象。可以将null赋值给任何引用类型的变量,包括类、接口、数组、字符串等。想了解更多null的相关内容,可以阅读本专题下面的文章。

436

2024.03.01

c语言const用法
c语言const用法

const是关键字,可以用于声明常量、函数参数中的const修饰符、const修饰函数返回值、const修饰指针。详细介绍:1、声明常量,const关键字可用于声明常量,常量的值在程序运行期间不可修改,常量可以是基本数据类型,如整数、浮点数、字符等,也可是自定义的数据类型;2、函数参数中的const修饰符,const关键字可用于函数的参数中,表示该参数在函数内部不可修改等等。

524

2023.09.20

Java JVM 原理与性能调优实战
Java JVM 原理与性能调优实战

本专题系统讲解 Java 虚拟机(JVM)的核心工作原理与性能调优方法,包括 JVM 内存结构、对象创建与回收流程、垃圾回收器(Serial、CMS、G1、ZGC)对比分析、常见内存泄漏与性能瓶颈排查,以及 JVM 参数调优与监控工具(jstat、jmap、jvisualvm)的实战使用。通过真实案例,帮助学习者掌握 Java 应用在生产环境中的性能分析与优化能力。

3

2026.01.20

热门下载

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

精品课程

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

共101课时 | 8.4万人学习

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号