宽松语法现时在这issue中进行讨论

日期:2019-08-30 23:09

  RapidJSON 是一个 C++ 库,用于解析及生成 JSON。读者可参考它的所有特点。

  是的,它在 MIT 特許條款下免费。它可用于商业软件。详情请参看license.txt。

  是的。在 Windows 上,一个解析 JSON 并打印出统计的可执行文件少于 30KB。

  社区已在多个操作系统/编译器/CPU 架构的组合上测试 RapidJSON。但我们无法确保它能运行于你特定的平台上。只需要生成及执行单元测试便能获取答案。

  是的。它被配置于前台及后台的真实应用中。一个社区成员说 RapidJSON 在他们的系统中每日解析 5 千万个 JSON。

  RapidJSON 包含一组单元测试去执行自动测试。Travis(供 Linux 平台)及AppVeyor(供 Windows 平台)会对所有修改进行编译及执行单元测试。在 Linux 下还会使用 Valgrind 去检测内存泄漏。

  JSON 常用于网页应用程序,以传送结构化数据。它也可作为文件格式用于数据持久化。

  现时不支持。RapidJSON 只支持严格的标准格式。宽松语法现时在这issue中进行讨论。

  原位解析会把 JSON 字符串直接解码至输入的 JSON 中。这是一个优化,可减少内存消耗及提升性能,但输入的 JSON 会被更改。进一步细节请参考原位解析。

  当输入的 JSON 包含非法语法,或不能表示一个值(如 Number 太大),或解析器的处理器中断解析过程,解析器都会产生一个错误。详情请参考解析错误。

  错误信息存储在ParseResult,它包含错误代号及偏移值(从 JSON 开始至错误处的字符数目)。可以把错误代号翻译为人类可读的错误讯息。

  一些应用需要使用 64 位无号/有号整数。这些整数不能无损地转换成double。因此解析器会检测一个 JSON number 是否能转换至各种整数类型及double。

  假设我们希望将整个address插入到person中,作为其的一个子节点:

  在插入节点的过程中需要注意document和value的生命周期并且正确地使用 allocator 进行内存分配和管理。

  一个简单有效的方法就是修改上述address变量的定义,让其使用person的 allocator 初始化,然后将其添加到根节点。

  当然,如果你不想通过显式地写出address的 key 来得到其值,可以使用迭代器来实现:

  Value不用复制语义,而使用了转移语义。这是指,当把来源值赋值于目标值时,来源值的所有权会转移至目标值。

  由于 C 字符串是空字符结尾的,需要使用strlen()去计算其长度,这是线性复杂度的操作。若使用者已知字符串的长度,对很多操作来说会造成不必要的消耗。

  此外,RapidJSON 可处理含有\u0000(空字符)的字符串。若一个字符串含有空字符,strlen()便不能返回真正的字符串长度。在这种情况下使用者必须明确地提供字符串长度。

  由于这些 API 是Value的成员函数,我们不希望为每个Value储存一个分配器指针。

  当使用GetInt()、GetUint()等 API 时,可能会发生转换。对于整数至整数转换,仅当保证转换安全才会转换(否则会断言失败)。然而,当把一个 64 位有号/无号整数转换至 double 时,它会转换,但有可能会损失精度。含有小数的数字、或大于 64 位的整数,都只能使用GetDouble()获取其值。

  最重要的是,Writer能确保输出的 JSON 是格式正确的。错误地调用 SAX 事件(如StartObject()错配EndArray())会造成断言失败。此外,Writer会把字符串进行转义(如\n)。最后,printf()的数值输出可能并不是一个合法的 JSON number,特别是某些 locale 会有数字分隔符。而且Writer的数值字符串转换是使用非常快的算法来实现的,胜过printf()及iostream。

  基于性能考虑,目前版本并不直接支持此功能。然而,若执行环境支持多线程,使用者可以在另一线程解析 JSON,并通过阻塞输入流去暂停。

  是。它完全支持 UTF-8、UTF-16(大端/小端)、UTF-32(大端/小端)及 ASCII。

  能。RapidJSON 完全支持 JSON 字符串中的空字符。然而,使用者需要注意到这件事,并使用GetStringLength()及相关 API 去取得字符串真正长度。

  可以。只要在Writer中使用ASCII作为输出编码参数,就可以强逼转义那些字符。

  使用者可使用FileReadStream去逐块读入文件。安博电竞但若使用于原位解析,必须载入整个文件。

  可以。使用者可根据FileReadStream的实现,去实现一个自定义的流。

  你可以使用AutoUTFInputStream,它能自动检测输入流的编码。然而,它会带来一些性能开销。

  字节顺序标记(byte order mark, BOM)有时会出现于文件/流的开始,以表示其 UTF 编码类型。

  流的大端/小端是 UTF-16 及 UTF-32 流要处理的问题,而 UTF-8 不需要处理。

  是。它可能是最快的开源 JSON 库。有一个评测评估 C/C++ JSON 库的性能。

  RapidJSON 的许多设计是针对时间/空间性能来设计的,这些决定可能会影响 API 的易用性。此外,它也使用了许多底层优化(内部函数/intrinsic、SIMD)及特别的算法(自定义的 double 至字符串转换、字符串至 double 的转换)。

  SIMD指令可以在现代 CPU 中执行并行运算。RapidJSON 支持使用 Intel 的 SSE2/SSE4.2 和 ARM 的 Neon 来加速对空白符、制表符、回车符和换行符的过滤处理。在解析含缩进的 JSON 时,这能提升性能。只要定义名为RAPIDJSON_SSE2,RAPIDJSON_SSE42或RAPIDJSON_NEON的宏,就能启动这个功能。然而,若在不支持这些指令集的机器上执行这些可执行文件,会导致崩溃。

  在 DOM API 中,每个Value在 32/64 位架构下分别消耗 16/24 字节。RapidJSON 也使用一个特殊的内存分配器去减少分配的额外开销。

  有些应用程序需要处理非常大的 JSON 文件。而有些后台应用程序需要处理大量的 JSON。达到高性能同时改善延时及吞吐量。更广义来说,这也可以节省能源。

  在 2011 年开始这项目是,它仅一个兴趣项目。Milo Yip 是一个游戏程序员,他在那时候认识到 JSON 并希望在未来的项目中使用。由于 JSON 好像很简单,他希望写一个仅有头文件并且快速的程序库。

  主要是个人因素,例如加入新家庭成员。另外,Milo Yip 也花了许多业馀时间去翻译 Jason Gregory 的《Game Engine Architecture》至中文版《游戏引擎架构》。