- Note
- 翻译最后更新时间:2026/2/27 13:01
翻译质量反馈:yyjson文档中文翻译
本文档包含了yyjson库所有API的用法和示例。
API设计
API前缀
所有公共函数和结构体都使用yyjson_作为前缀,所有常量包括宏定义都使用YYJSON_作为前缀。
可变/不可变数据的API
本库有两种数据结构:不可变(immutable)数据和可变(mutable)数据。
当读取JSON时,yyjson返回不可变文档和值。
当构建JSON时,yyjson创建可变文档和值。
文档管理所有JSON值与字符串的内存。
对于大多数不可变API,你可以在yyjson_后面加一个mut使之变为可变版本,例如:
yyjson_api_inline bool yyjson_is_str(yyjson_val *val)
Definition yyjson.h:5287
yyjson_api_inline char * yyjson_mut_write(const yyjson_mut_doc *doc, yyjson_write_flag flg, size_t *len)
Definition yyjson.h:1515
yyjson_api_inline char * yyjson_write(const yyjson_doc *doc, yyjson_write_flag flg, size_t *len)
Definition yyjson.h:1386
yyjson_api_inline bool yyjson_mut_is_str(yyjson_mut_val *val)
Definition yyjson.h:5858
库中也提供了一些可以将值在可变与不可变之间相互转换的函数:
yyjson_api yyjson_mut_val * yyjson_val_mut_copy(yyjson_mut_doc *doc, yyjson_val *val)
yyjson_api yyjson_mut_doc * yyjson_doc_mut_copy(yyjson_doc *doc, const yyjson_alc *alc)
yyjson_api yyjson_doc * yyjson_mut_doc_imut_copy(yyjson_mut_doc *doc, const yyjson_alc *alc)
yyjson_api yyjson_doc * yyjson_mut_val_imut_copy(yyjson_mut_val *val, const yyjson_alc *alc)
字符串API
本库支持带或不带空终止符('\0')的字符串。
当你想要使用无空终止符的字符串或者当你清楚的知道字符串长度的时候,你可以使用结尾为字母n的函数,例如:
yyjson_api_inline bool yyjson_equals_str(yyjson_val *val, const char *str)
Definition yyjson.h:5374
yyjson_api_inline bool yyjson_equals_strn(yyjson_val *val, const char *str, size_t len)
Definition yyjson.h:5382
为了获得更好的性能,yyjson在创建JSON时会将字符串视为常量。当然,如果你的字符串可能被修改,需要使用带有cpy字样的函数以将字符串复制进文档,例如:
yyjson_api_inline yyjson_mut_val * yyjson_mut_strn(yyjson_mut_doc *doc, const char *str, size_t len)
Definition yyjson.h:6162
yyjson_api_inline yyjson_mut_val * yyjson_mut_strncpy(yyjson_mut_doc *doc, const char *str, size_t len)
Definition yyjson.h:6181
yyjson_api_inline yyjson_mut_val * yyjson_mut_strcpy(yyjson_mut_doc *doc, const char *str)
Definition yyjson.h:6168
yyjson_api_inline yyjson_mut_val * yyjson_mut_str(yyjson_mut_doc *doc, const char *str)
Definition yyjson.h:6157
读取JSON
本库提供了五个读JSON的函数。
每个函数接受一个UTF-8编码的数据或文件作为输入。
如果成功,函数返回一个文档,失败则返回NULL。
从字符串读取JSON
dat参数接受一个UTF-8字符串,不需要空终止符。
len参数是dat中字符串的字节长度
flg是读取器标志,不需要时可传入 0,详见读取器标志。
加入输入是不合法的,函数会返回NULL。
size_t len,
uint32_t yyjson_read_flag
Definition yyjson.h:726
yyjson_api_inline yyjson_doc * yyjson_read(const char *dat, size_t len, yyjson_read_flag flg)
Definition yyjson.h:989
示例代码:
const char *str = "[1,2,3,4]";
if (doc) {...}
yyjson_api_inline void yyjson_doc_free(yyjson_doc *doc)
Definition yyjson.h:5232
从文件读JSON
path参数接受一个JSON文件的路径。要求使用系统原生编码的带空终止符的字符串。
flg参数是读取器标志,不需要时可传入 0,详见读取器标志。
alc参数用于指定内存分配器,如果不需要请传入NULL,详见内存分配器。
err参数是一个接受错误信息的指针,如果不需要请传入NULL。
假如输入是不合法的,函数会返回NULL。
yyjson_api yyjson_doc * yyjson_read_file(const char *path, yyjson_read_flag flg, const yyjson_alc *alc, yyjson_read_err *err)
示例代码:
从文件指针读取JSON
fp参数接受一个文件指针。yyjson会从文件的当前位置到结尾读取数据。
flg参数是读取器标志,不需要时可传入 0,详见读取器标志。
alc参数用于指定内存分配器,如果不需要请传入NULL,详见内存分配器。
err参数是一个接受错误信息的指针,如果不需要请传入NULL。
假如输入是不合法的,函数会返回NULL。
yyjson_api yyjson_doc * yyjson_read_fp(FILE *fp, yyjson_read_flag flg, const yyjson_alc *alc, yyjson_read_err *err)
示例代码:
FILE *fp = fdopen(fd, "rb");
if (fp) fclose(fp);
if (doc) {...}
带选项读取JSON
dat参数接受一个UTF-8字符串。 假如你没有在flg参数处使用YYJSON_READ_INSITU标志则可以传入一个字符串常量。
len参数是dat中字符串的字节长度
flg参数是读取器标志,不需要时可传入 0,详见读取器标志。
alc参数用于指定内存分配器,如果不需要请传入NULL,详见内存分配器。
err参数是一个接受错误信息的指针,如果不需要请传入NULL。
假如输入是不合法的,函数会返回NULL。
size_t len,
yyjson_api yyjson_doc * yyjson_read_opts(char *dat, size_t len, yyjson_read_flag flg, const yyjson_alc *alc, yyjson_read_err *err)
示例代码:
const char *dat = your_file.bytes;
size_t len = your_file.size;
if (doc) {...}
static const yyjson_read_flag YYJSON_READ_ALLOW_INF_AND_NAN
Definition yyjson.h:760
static const yyjson_read_flag YYJSON_READ_ALLOW_COMMENTS
Definition yyjson.h:756
增量读取JSON
读取一个很大的JSON文档可能会短暂的冻结程序,假如这是不可接受的,可以选择使用增量读取。
仅当文档较大且程序需要及时响应时,才推荐使用增量读取;此方法相较于yyjson_read()和yyjson_read_opts()会略慢一些。
注意:增量读取仅支持标准的JSON语法。 非标准的功能标志(比如注释, 尾随逗号)会被忽略。
下面是增量读取大体积JSON文档的流程:
- 调用
yyjson_incr_new()来创建一个增量阅读状态(state)对象。
- 反复调用
yyjson_incr_read()。
- 调用
yyjson_incr_free()以释放状态对象。
为增量阅读创建状态对象
buf参数接收一个不需要空结束符的UTF-8字符串。 假如你没有在flg参数处使用YYJSON_READ_INSITU标志则可以传入一个字符串常量。
buf_len参数是buf中字符串的字节长度。 flg参数是读取器标志,不需要时可传入 0,详见读取器标志。
alc参数用于指定内存分配器,如果不需要请传入NULL,详见内存分配器。
正常情况下这个函数会返回一个新的状态,但如果flg参数是无效的或者内存分配器发生了故障,函数返回NULL
struct yyjson_incr_state yyjson_incr_state
Definition yyjson.h:1002
yyjson_api yyjson_incr_state * yyjson_incr_new(char *buf, size_t buf_len, yyjson_read_flag flg, const yyjson_alc *alc)
执行增量读取
执行最多len字节的增量读取。
增量读取的state参数由yyjson_incr_new()创建。
len参数表示从JSON数据开头开始计数的要读取的最大字节数。
err参数是一个接受错误信息的指针,本参数不可空。
当读取完成时,本函数返回一个文档对象,否则返回NULL。 假如err->code被设置为了YYJSON_READ_ERROR_MORE,意味着语法解析没有完成。 此时,需要将len增加几千字节(KB),随后重新调用本函数。 持续增加len直到len == buf_len(达到输入缓冲区的总长度)或者直到返回一个不是YYJSON_READ_ERROR_MORE的错误。
注意: 增量很小时语法分析效率不高。 建议单次增量几千字节或几兆字节(MB)
译者注:其实YYJSON_READ_ERROR_MORE不算错误,实际上已经正确读取了数据,只是没读完需要更多数据罢了,不知道你们能不能理解这个,反正我一开始没绕过来...
yyjson_api yyjson_doc * yyjson_incr_read(yyjson_incr_state *state, size_t len, yyjson_read_err *err)
释放用于增量读取的状态
释放由yyjson_incr_new()创建的state.
yyjson_api void yyjson_incr_free(yyjson_incr_state *state)
示例代码
const char *dat = your_file.bytes;
size_t len = your_file.size;
size_t read_so_far = 0;
do {
read_so_far += 100000;
if (read_so_far > len)
read_so_far = len;
break;
} while (read_so_far < len);
if (doc != NULL) { ... }
static const yyjson_read_code YYJSON_READ_ERROR_MORE
Definition yyjson.h:879
yyjson_read_code code
Definition yyjson.h:887
static const yyjson_read_flag YYJSON_READ_NOFLAG
Definition yyjson.h:736
读取器错误处理
当JSON读取失败且需要错误信息时,可向调用的yyjson_read_xxx()函数传递一个yyjson_read_err指针来接收详细的错误信息。
示例代码:
char *dat = ...;
size_t dat_len = ...;
if (!doc) {
printf("读取错误: %s,错误码:%u,位置:第%lu字节\n",
}
size_t pos
Definition yyjson.h:891
const char * msg
Definition yyjson.h:889
错误信息中的pos标明了错误发生在的字节位置。假如你需要错误的行号和列号,可以使用yyjson_locate_pos()函数。需要注意的是行(line)与列(column)是从1开始的而字符(character)是从0开始的。上述所有值都是基于Unicode字符计算的,以便更好的兼容绝大多数的文本编辑器
示例代码:
char *dat = ...;
size_t dat_len = ...;
size_t line, col, chr;
printf("错误发生在第 %lu 行 第 %lu 列,字符索引:%lu\n",
line, col, chr);
}
yyjson_api bool yyjson_locate_pos(const char *str, size_t len, size_t pos, size_t *line, size_t *col, size_t *chr)
读取器标志
本库提供了一组JSON读取器标志。
你可以单独使用一个标志,或者使用按位或操作符|将多个标志结合在一起。
非标准的标志(比如YYJSON_READ_JSON5,支持JSON 5 语法)在读取标准JSON输入时不会影响性能
YYJSON_READ_NOFLAG = 0
这是JSON读取器的默认标志(遵循RFC-8259或ECMA-404):
- 将正整数读入
uint64_t。
- 将负整数读入
int64_t。
- 将浮点数正确四舍五入后读入
double。
- 对于超出
uint64_t或int64_t范围的整数读入double。
- 当double型数值为无穷大时报错。
- 当字符串包含非法的UTF-8字符或BOM时报错。
- 遇到尾随逗号、注释、
Inf和NaN字面值时报错。
YYJSON_READ_INSITU
就地读取数据(不拷贝)。
这个选项允许读取器修改并使用输入数据来存储字符串值,这样可以略微提升读取速度,但调用者必须确保在文档被释放之前输入数据一直有效。输入数据必须至少填充YYJSON_PADDING_SIZE字节的额外空间。例如:[1,2]应写为[1,2]\0\0\0\0,输入长度应为5(填充字节不计入)。
示例代码:
size_t dat_len = ...;
read_from_socket(buf, ...);
if (doc) {...}
free(buf);
static const yyjson_read_flag YYJSON_READ_INSITU
Definition yyjson.h:744
#define YYJSON_PADDING_SIZE
Definition yyjson.h:575
YYJSON_READ_STOP_WHEN_DONE
当到达JSON文档的末尾是就停止解析,即使后面有附加内容也不报错。
这个选项对于解析大体积的JSON的一小部分是很有用的,像是NDJSON这样。(译者注:国内打不开维基百科,请自行寻找镜像替代)
示例代码:
size_t file_size = ...;
char *dat = malloc(file_size + 4);
your_read_file(dat, file);
memset(dat + file_size, 0, 4);
char *hdr = dat;
char *end = dat + file_size;
while (true) {
if (!doc) break;
your_doc_process(doc);
}
free(dat);
yyjson_api_inline size_t yyjson_doc_get_read_size(yyjson_doc *doc)
Definition yyjson.h:5224
static const yyjson_read_flag YYJSON_READ_STOP_WHEN_DONE
Definition yyjson.h:749
YYJSON_READ_ALLOW_TRAILING_COMMAS
允许在对象或数组尾部出现单个尾随逗号(非标准),例如:
{
"a": 1,
"b": 2,
}
[
"a",
"b",
]
YYJSON_READ_ALLOW_COMMENTS
允许C风格的单行和多行注释(非标准),例如:
{
"name": "玉墨", // 单行注释
"id": /* 多行注释 */ 114514
}
YYJSON_READ_ALLOW_INF_AND_NAN
允许NaN和Inf以及其他不区分大小写的字面量,例如:
{
"large": 123e999,
"nan1": NaN,
"nan2": nan,
"inf1": Inf,
"inf2": -Infinity
}
YYJSON_READ_NUMBER_AS_RAW
将所有数字以原始字符串读入而不做解析处理。
如果你想自己解析数字,这个标志就十分有用。 你可以使用下面这些函数来提取原始字符串:
yyjson_api_inline bool yyjson_is_raw(yyjson_val *val)
Definition yyjson.h:5247
yyjson_api_inline const char * yyjson_get_raw(yyjson_val *val)
Definition yyjson.h:5338
yyjson_api_inline size_t yyjson_get_len(yyjson_val *val)
Definition yyjson.h:5370
YYJSON_READ_BIGNUM_AS_RAW
将大数以原始字符串读入。
如果你想自己解析大数(比如你有个高精模拟什么的)这个标志就很有用 大数包括不能被int64_t和uint64_t表示的整数以及不能被有限的double表示的浮点数
需要注意的是这个标志会被YYJSON_READ_NUMBER_AS_RAW标志覆盖
YYJSON_READ_ALLOW_INVALID_UNICODE
解析字符串时允许读取无效的Unicode(非标准), 例如:
"\x80xyz"
"\xF0\x81\x81\x81"
这个标志允许无效的字符出现在字符串值中,但是仍然会对无效的转义序列报错。标志不会影响正确编码字符串的性能。
警告: 使用这个选项时,请小心JSON内的字符串可能会包含的错误编码,你需要谨慎的处理这些字符串以避免安全问题。
YYJSON_READ_ALLOW_BOM
允许带BOM的UTF-8并在解析前跳过BOM(非标准)。
YYJSON_READ_ALLOW_EXT_NUMBER
允许扩展的数字格式(非标准):
- 十六进制数字,比如
0x7B。
- 带有前导或尾随小数点的数字,比如
.123、123.。
- 带有前导加号的数字,比如
+123。
YYJSON_READ_ALLOW_EXT_ESCAPE
在字符串中允许扩展的转义序列(非标准)
- 一些额外的转义:
\a、\e、\v、\'、\?、\0。
- 十六进制转义:形如
\xNN,比如\x7B。
- 续行符: 反斜线后跟随行终止符序列。
- 未知的转义:假如反斜线跟随了一个不支持的字符, 则反斜线将被删除,跟随的字符原被样保留。 当然,
\1-\9仍然会触发错误。
YYJSON_READ_ALLOW_EXT_WHITESPACE
允许扩展的空白符(非标准)
- 垂直制表符
\v和换页符\f。
- 行分隔符
\u2028和段落分隔符\u2029。
- 不间断空格
\xA0。
- 字节顺序标记:
\uFEFF。
- 其他处于Unicode Zs(空格、分隔符)分类下的字符。
YYJSON_READ_ALLOW_SINGLE_QUOTED_STR
允许使用被单引号括起来的字符串(非标准),比如'ab'。
YYJSON_READ_ALLOW_UNQUOTED_KEY
允许对象键不带引号(非标准),例如{a:1,b:2}。该选项扩展了 ECMAScript 的标识符名称规则,允许使用任何码点高于U+007F的非空白字符。
译者注:这里的意思就是Unicode内超出ASCII范围(高于U+007F)的所有非空白字符都可以直接用作对象键,无需加引号;而ASCII范围内的部分符号必须由引号包裹比如-,这些符号往往是在JSON中发挥作用的特殊符号
YYJSON_READ_JSON5
允许JSON5格式,有关JSON5请见:https://json5.org。 Allow JSON5 format, see: https://json5.org.
这个标志在支持所有JSON5功能的基础上还额外附加了一些扩展功能:
- 相较于JSON5而言能接收更多的转义序列(比如
\a、\e)。
- 无引号的键不被ECMAScript标识符名称规则所限制。
- 允许大小写不敏感的
NaN、Inf和Infinity字面量。
例如:
{
/* JSON5示例 */
id: 123,
name: 'Yumo-sama',
color_argb: 0x0d000721,
min: .001,
max: Inf,
data: '\x00\xAA\xFF',
}
写出JSON
本库提供了五组用于写出JSON的函数。
每个函数都接受一个JSON文档对象或根值对象(译者注:yyjson_doc或yyjson_val)作为输入,并返回一个UTF-8字符串或文件。
将JSON写入字符串
doc/val参数接收一个JSON文档对象或根值对象,假如你传递的是NULL,你得到的返回值也是NULL。
flg参数是写出器标志,如果不需要就传入0,详见写出器标志。
len是一个用来接收输出文本长度的指针(空结束符不算在长度内),如不需要,请传递NULL。 。
正常情况下函数返回一个新的JSON字符串;如果有错误发生,则会返回NULL。
字符串以UTF-8编码,尾部带有空结束符。
在你不需要再使用这个字符串时,需要使用free()或alc->free()来释放它。
yyjson_api_inline char * yyjson_val_write(const yyjson_val *val, yyjson_write_flag flg, size_t *len)
Definition yyjson.h:1645
yyjson_api_inline char * yyjson_mut_val_write(const yyjson_mut_val *val, yyjson_write_flag flg, size_t *len)
Definition yyjson.h:1772
uint32_t yyjson_write_flag
Definition yyjson.h:1161
示例代码1:
printf("%s\n", json);
free(json);
static const yyjson_write_flag YYJSON_WRITE_PRETTY
Definition yyjson.h:1171
示例代码2:
printf("%s\n", json);
free(json);
yyjson_api_inline void yyjson_mut_doc_set_root(yyjson_mut_doc *doc, yyjson_mut_val *root)
Definition yyjson.h:5807
yyjson_api_inline bool yyjson_mut_arr_add_int(yyjson_mut_doc *doc, yyjson_mut_val *arr, int64_t num)
Definition yyjson.h:6748
yyjson_api yyjson_mut_doc * yyjson_mut_doc_new(const yyjson_alc *alc)
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr(yyjson_mut_doc *doc)
Definition yyjson.h:6296
将JSON写入文件
path参数指定输出的JSON文件路径,其应当是一个使用系统原生编码的以空终止符结尾的字符串。假如传递的路径是无效的,你将收到一条报错;假如文件是非空的,原本的内容会被覆盖掉。
doc/val参数是JSON文档对象或根值对象,传入NULL则会触发报错。
flg参数是写出器标志,如不需要请传入0,详见写出器标志。
alc参数用于指定内存分配器,如不需要请传入NULL,详见内存分配器。
err参数用于指定一个接受错误信息的指针,如果不需要请传入NULL。
函数在成功时返回true,发生错误时返回假。
yyjson_api bool yyjson_write_file(const char *path, const yyjson_doc *doc, yyjson_write_flag flg, const yyjson_alc *alc, yyjson_write_err *err)
yyjson_api bool yyjson_val_write_file(const char *path, const yyjson_val *val, yyjson_write_flag flg, const yyjson_alc *alc, yyjson_write_err *err)
yyjson_api bool yyjson_mut_write_file(const char *path, const yyjson_mut_doc *doc, yyjson_write_flag flg, const yyjson_alc *alc, yyjson_write_err *err)
yyjson_api bool yyjson_mut_val_write_file(const char *path, const yyjson_mut_val *val, yyjson_write_flag flg, const yyjson_alc *alc, yyjson_write_err *err)
示例代码:
将JSON写入文件指针
fp参数是用于输出的文件指针,数据将被写到文件的当前位置。
doc/val参数是JSON文档对象或者根值对象,传递NULL将触发错误。
flg参数是写出器标志,如不需要请传入0,详见写出器标志。
alc参数指定内存分配器,如不需要请传入NULL,详见内存分配器。
err参数用于指定一个接受错误信息的指针,如果不需要请传入NULL。
函数在成功时返回true,发生错误时返回假。
yyjson_api bool yyjson_write_fp(FILE *fp, const yyjson_doc *doc, yyjson_write_flag flg, const yyjson_alc *alc, yyjson_write_err *err)
yyjson_api bool yyjson_val_write_fp(FILE *fp, const yyjson_val *val, yyjson_write_flag flg, const yyjson_alc *alc, yyjson_write_err *err)
yyjson_api bool yyjson_mut_write_fp(FILE *fp, const yyjson_mut_doc *doc, yyjson_write_flag flg, const yyjson_alc *alc, yyjson_write_err *err)
yyjson_api bool yyjson_mut_val_write_fp(FILE *fp, const yyjson_mut_val *val, yyjson_write_flag flg, const yyjson_alc *alc, yyjson_write_err *err)
示例代码:
FILE *fp = fdopen(fd, "wb");
if (fp) fclose(fp);
if (suc) printf("完成");
将JSON写入缓冲区
buf参数指定输出缓冲区,传递NULL时函数将返回0。
buf_len参数指定输出缓冲区的长度,假如长度过小,函数会失败并返回0。
doc/val参数接收一个JSON文档对象或根值对象,传入NULL则会触发报错。
flg参数是写出器标志,如不需要请传入0,详见写出器标志。
err参数用于指定一个接受错误信息的指针,如果不需要请传入NULL。
函数正常会返回写出内容的字节长度(包含空终止符),失败时则会返回0。
该函数不会分配内存,但缓冲区必须大于最终的JSON大小,以为临时操作留出空间。
每个值在写入时都要临时占据一块额外的空间,这块空间将被后面的值重用:
- 数字:
40字节
- 字符串:
16 + (str_len * 6)字节
- 其他值:
16字节
- 嵌套深度:
16 * max_json_depth字节
yyjson_api size_t yyjson_write_buf(char *buf, size_t buf_len, const yyjson_doc *doc, yyjson_write_flag flg, yyjson_write_err *err)
yyjson_api size_t yyjson_mut_val_write_buf(char *buf, size_t buf_len, const yyjson_mut_val *val, yyjson_write_flag flg, yyjson_write_err *err)
yyjson_api size_t yyjson_val_write_buf(char *buf, size_t buf_len, const yyjson_val *val, yyjson_write_flag flg, yyjson_write_err *err)
yyjson_api size_t yyjson_mut_write_buf(char *buf, size_t buf_len, const yyjson_mut_doc *doc, yyjson_write_flag flg, yyjson_write_err *err)
示例代码:
char buf[512];
if (len > 0) printf("完成,输出内容:\n%s\n", buf);
带选项的写出JSON
doc/val参数接收一个JSON文档对象或根值对象,假如你传递的是NULL,你得到的返回值也是NULL。
flg参数是写出器标志,如果不需要就传入0,详见写出器标志。
alc参数用于指定内存分配器,如不需要请传入NULL,详见内存分配器。
len是一个用来接收输出文本长度的指针(空结束符不算在长度内),如不需要,请传递NULL。 。
err参数用于指定一个接受错误信息的指针,如果不需要请传入NULL。
正常情况下函数返回一个新的JSON字符串;如果有错误发生,则会返回NULL。
字符串以UTF-8编码,尾部带有空结束符。
在你不需要再使用这个字符串时,需要使用free()或alc->free()来释放它。
yyjson_api char * yyjson_write_opts(const yyjson_doc *doc, yyjson_write_flag flg, const yyjson_alc *alc, size_t *len, yyjson_write_err *err)
yyjson_api char * yyjson_val_write_opts(const yyjson_val *val, yyjson_write_flag flg, const yyjson_alc *alc, size_t *len, yyjson_write_err *err)
yyjson_api char * yyjson_mut_write_opts(const yyjson_mut_doc *doc, yyjson_write_flag flg, const yyjson_alc *alc, size_t *len, yyjson_write_err *err)
yyjson_api char * yyjson_mut_val_write_opts(const yyjson_mut_val *val, yyjson_write_flag flg, const yyjson_alc *alc, size_t *len, yyjson_write_err *err)
示例代码:
char buf[64 * 1024];
size_t len;
if (json) {
printf("成功: %lu\n%s\n", len, json);
} else {
printf(
"错误:%u msg:%s\n", err.
code, err.
msg);
}
void(* free)(void *ctx, void *ptr)
Definition yyjson.h:595
void * ctx
Definition yyjson.h:597
const char * msg
Definition yyjson.h:1257
yyjson_api bool yyjson_alc_pool_init(yyjson_alc *alc, void *buf, size_t size)
static const yyjson_write_flag YYJSON_WRITE_ESCAPE_UNICODE
Definition yyjson.h:1174
yyjson_write_code code
Definition yyjson.h:1255
写出器标志
本库提供了一组JSON写出器标志。
你可以单独使用一个标志,或者使用按位或操作符|将多个标志结合在一起。
YYJSON_WRITE_NOFLAG = 0
本标志是JSON写出器的默认标志:
- 用压缩格式写出JSON(去除不必要的缩进)
- 处理数字时遇到
inf或nan将报错。
- 处理字符串时遇到无效的Unicode字符将报错。
- 不转义Unicode字符或斜杠。
YYJSON_WRITE_PRETTY
用带有四个空格缩进的更漂亮的格式输出JSON。
YYJSON_WRITE_PRETTY_TWO_SPACES
用带有两个空格缩进的更漂亮的格式输出JSON。 本标志将会覆盖YYJSON_WRITE_PRETTY标志。
YYJSON_WRITE_ESCAPE_UNICODE
将Unicode转义为\uXXXX格式,保证输出内容只有ASCII字符,例如:
["Alizée, 😊, 小狄同学呀"]
["Aliz\\u00E9e, \\uD83D\\uDE0A, \\u5C0F\\u72C4\\u540C\\u5B66\\u5440"]
YYJSON_WRITE_ESCAPE_SLASHES
将正斜杠/转义为\/,例如:
["https://github.com"]
["https:\/\/github.com"]
YYJSON_WRITE_ALLOW_INF_AND_NAN
将inf(无穷大)/nan(非数值)的数字写出为Infinity和NaN字面值而不是报错。
注意这个输出**不是**JSON的标准写法且别的JSON库可能无法解析。
示例输出:
{"not_a_number":NaN,"large_number":Infinity}
YYJSON_WRITE_INF_AND_NAN_AS_NULL
将inf(无穷大)/nan(非数值)的数字写出为null字面量而不是报错。
本标志将覆盖YYJSON_WRITE_ALLOW_INF_AND_NAN标志。
输出示例:
{"not_a_number":null,"large_number":null}
YYJSON_WRITE_ALLOW_INVALID_UNICODE
在编码字符串值时允许无效的Unicode。
字符串中无效的字符将会被原样逐字节复制。如果同时还设置了YYJSON_WRITE_ESCAPE_UNICODE标志,则无效字符将被转义为\uFFFD(替换字符)。
本标志在字符串编码正确时不会影响性能。
YYJSON_WRITE_NEWLINE_AT_END
在JSON的末尾加上一个换行符\n。 这对文本编辑器或NDJSON更加友好。
YYJSON_WRITE_FP_TO_FLOAT
使用单精度(float)写出浮点数。 这将会把double在序列化前转换为float。 用这种方法产生的输出更短但是可能会失去一些精度。 当YYJSON_WRITE_FP_TO_FIXED(prec)标志被同时使用时,本标志将失效。
YYJSON_WRITE_FP_TO_FIXED(prec)
使用定点表示法写入浮点数。 这类似于 ECMAScript 的Number.prototype.toFixed(prec),但会移除末尾的零。prec的取值范围为 1 到 15。 这样产生的输出更短,但可能会损失一些精度。
访问JSON文档
JSON文档
你可有用下面的这些函数来访问JSON文档对象的内容:
yyjson_api_inline size_t yyjson_doc_get_val_count(yyjson_doc *doc)
Definition yyjson.h:5228
yyjson_api_inline yyjson_val * yyjson_doc_get_root(yyjson_doc *doc)
Definition yyjson.h:5220
文档对象持有其内部所有值和字符串的内存。当你不再需要它时,应释放该文档对象以回收所有内存:
JSON值对象
每一个JSON值对象都有一个类型和子类型,如下表所示:
| 类型 | 子类型 | 解释 |
| YYJSON_TYPE_NONE | | 无效值 |
| YYJSON_TYPE_RAW | | 原始字符串 |
| YYJSON_TYPE_NULL | | null字面量 |
| YYJSON_TYPE_BOOL | YYJSON_SUBTYPE_FALSE | false字面量 |
| YYJSON_TYPE_BOOL | YYJSON_SUBTYPE_TRUE | true字面量 |
| YYJSON_TYPE_NUM | YYJSON_SUBTYPE_UINT | uint64_t数字 |
| YYJSON_TYPE_NUM | YYJSON_SUBTYPE_SINT | int64_t数字 |
| YYJSON_TYPE_NUM | YYJSON_SUBTYPE_REAL | double数字 |
| YYJSON_TYPE_STR | | 字符串值 |
| YYJSON_TYPE_STR | YYJSON_SUBTYPE_NOESC | 字符串值,无转义 |
| YYJSON_TYPE_ARR | | 数组值 |
| YYJSON_TYPE_OBJ | | 对象值 |
YYJSON_TYPE_NONE表示无效值,它不会在JSON文档解析成功时出现。
YYJSON_TYPE_RAW只在使用了YYJSON_READ_XXX_AS_RAW这类标志时才会出现。
YYJSON_SUBTYPE_NOESC用于优化无需转义的字符串的写出速度。此子类型仅在内部使用,用户无需处理。
下面的函数被用来确定JSON值对象的类型:
uint8_t yyjson_subtype
Definition yyjson.h:541
yyjson_api_inline bool yyjson_is_ctn(yyjson_val *val)
Definition yyjson.h:5299
yyjson_api_inline uint8_t yyjson_get_tag(yyjson_val *val)
Definition yyjson.h:5317
yyjson_api_inline bool yyjson_is_bool(yyjson_val *val)
Definition yyjson.h:5263
yyjson_api_inline bool yyjson_is_real(yyjson_val *val)
Definition yyjson.h:5279
yyjson_api_inline const char * yyjson_get_type_desc(yyjson_val *val)
Definition yyjson.h:5321
uint8_t yyjson_type
Definition yyjson.h:522
yyjson_api_inline bool yyjson_is_int(yyjson_val *val)
Definition yyjson.h:5275
yyjson_api_inline bool yyjson_is_true(yyjson_val *val)
Definition yyjson.h:5255
yyjson_api_inline bool yyjson_is_false(yyjson_val *val)
Definition yyjson.h:5259
yyjson_api_inline yyjson_subtype yyjson_get_subtype(yyjson_val *val)
Definition yyjson.h:5313
yyjson_api_inline yyjson_type yyjson_get_type(yyjson_val *val)
Definition yyjson.h:5309
yyjson_api_inline bool yyjson_is_null(yyjson_val *val)
Definition yyjson.h:5251
yyjson_api_inline bool yyjson_is_sint(yyjson_val *val)
Definition yyjson.h:5271
yyjson_api_inline bool yyjson_is_uint(yyjson_val *val)
Definition yyjson.h:5267
yyjson_api_inline bool yyjson_is_arr(yyjson_val *val)
Definition yyjson.h:5291
yyjson_api_inline bool yyjson_is_num(yyjson_val *val)
Definition yyjson.h:5283
yyjson_api_inline bool yyjson_is_obj(yyjson_val *val)
Definition yyjson.h:5295
使用下面的函数可以获取JSON值对象的内容。
yyjson_api_inline int yyjson_get_int(yyjson_val *val)
Definition yyjson.h:5354
yyjson_api_inline double yyjson_get_real(yyjson_val *val)
Definition yyjson.h:5358
yyjson_api_inline const char * yyjson_get_str(yyjson_val *val)
Definition yyjson.h:5366
yyjson_api_inline bool yyjson_get_bool(yyjson_val *val)
Definition yyjson.h:5342
yyjson_api_inline uint64_t yyjson_get_uint(yyjson_val *val)
Definition yyjson.h:5346
yyjson_api_inline double yyjson_get_num(yyjson_val *val)
Definition yyjson.h:5362
yyjson_api_inline int64_t yyjson_get_sint(yyjson_val *val)
Definition yyjson.h:5350
下面的函数可以用来修改JSON值对象的内容。
警告:对于不可变文档,这些函数将会打破“不可变”的约定,你需要谨慎的使用这组API(例如:保证涉及的文档只能在单线程中访问)。
yyjson_api_inline bool yyjson_set_null(yyjson_val *val)
Definition yyjson.h:5405
yyjson_api_inline bool yyjson_set_raw(yyjson_val *val, const char *raw, size_t len)
Definition yyjson.h:5398
yyjson_api_inline bool yyjson_set_uint(yyjson_val *val, uint64_t num)
Definition yyjson.h:5417
yyjson_api_inline bool yyjson_set_str(yyjson_val *val, const char *str)
Definition yyjson.h:5465
yyjson_api_inline bool yyjson_set_strn(yyjson_val *val, const char *str, size_t len)
Definition yyjson.h:5472
yyjson_api_inline bool yyjson_set_float(yyjson_val *val, float num)
Definition yyjson.h:5435
yyjson_api_inline bool yyjson_set_int(yyjson_val *val, int64_t num)
Definition yyjson.h:5429
yyjson_api_inline bool yyjson_set_real(yyjson_val *val, double num)
Definition yyjson.h:5447
yyjson_api_inline bool yyjson_set_double(yyjson_val *val, double num)
Definition yyjson.h:5441
yyjson_api_inline bool yyjson_set_sint(yyjson_val *val, int64_t num)
Definition yyjson.h:5423
yyjson_api_inline bool yyjson_set_bool(yyjson_val *val, bool num)
Definition yyjson.h:5411
JSON数组
下面的这些函数可以用来访问JSON数组。
注意,通过索引访问数组元素可能需要线性搜索时间。(译者注:耗时与数组大小呈线性关系,时间复杂度O(n)。)所以如果你想要遍历整个数组,更推荐使用迭代器API。
yyjson_api_inline size_t yyjson_arr_size(yyjson_val *arr)
Definition yyjson.h:5492
yyjson_api_inline yyjson_val * yyjson_arr_get_last(yyjson_val *arr)
Definition yyjson.h:5520
yyjson_api_inline yyjson_val * yyjson_arr_get(yyjson_val *arr, size_t idx)
Definition yyjson.h:5496
yyjson_api_inline yyjson_val * yyjson_arr_get_first(yyjson_val *arr)
Definition yyjson.h:5511
JSON数组迭代器
遍历数组有下面两种方法:
示例代码1(迭代器API):
your_func(val);
}
yyjson_api_inline yyjson_arr_iter yyjson_arr_iter_with(yyjson_val *arr)
Definition yyjson.h:5554
yyjson_api_inline yyjson_val * yyjson_arr_iter_next(yyjson_arr_iter *iter)
Definition yyjson.h:5564
示例代码2 (foreach宏):
size_t idx, max;
your_func(idx, val);
}
#define yyjson_arr_foreach(arr, idx, max, val)
Definition yyjson.h:2148
还有一个可变版本API,用来遍历可变数组:
示例代码1(可变迭代器API):
if (your_val_is_unused(val)) {
}
}
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_iter_remove(yyjson_mut_arr_iter *iter)
Definition yyjson.h:6273
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_iter_next(yyjson_mut_arr_iter *iter)
Definition yyjson.h:6261
yyjson_api_inline yyjson_mut_arr_iter yyjson_mut_arr_iter_with(yyjson_mut_val *arr)
Definition yyjson.h:6250
示例代码2 (可变的foreach宏):
size_t idx, max;
your_func(idx, val);
}
#define yyjson_mut_arr_foreach(arr, idx, max, val)
Definition yyjson.h:2883
JSON对象
下面的函数可以用来访问JSON对象:
注意,按对象键访问元素可能需要线性搜索时间。因此,如果需要遍历一个对象,建议使用迭代器API。
yyjson_api_inline yyjson_val * yyjson_obj_get(yyjson_val *obj, const char *key)
Definition yyjson.h:5585
yyjson_api_inline yyjson_val * yyjson_obj_iter_get(yyjson_obj_iter *iter, const char *key)
Definition yyjson.h:5647
yyjson_api_inline yyjson_val * yyjson_obj_getn(yyjson_val *obj, const char *key, size_t key_len)
Definition yyjson.h:5590
yyjson_api_inline yyjson_obj_iter yyjson_obj_iter_with(yyjson_val *obj)
Definition yyjson.h:5623
yyjson_api_inline size_t yyjson_obj_size(yyjson_val *obj)
Definition yyjson.h:5581
JSON对象迭代器
有两种遍历对象的方法:
示例代码1(迭代器API):
your_func(key, val);
}
yyjson_api_inline yyjson_val * yyjson_obj_iter_get_val(yyjson_val *key)
Definition yyjson.h:5643
yyjson_api_inline yyjson_val * yyjson_obj_iter_next(yyjson_obj_iter *iter)
Definition yyjson.h:5633
示例代码2(foreach宏):
size_t idx, max;
your_func(key, val);
}
#define yyjson_obj_foreach(obj, idx, max, key, val)
Definition yyjson.h:2319
还有一个可变版本的API用于遍历可变对象:
示例代码1(可变迭代器API):
if (your_key_is_unused(key)) {
}
}
yyjson_api_inline yyjson_mut_val * yyjson_mut_obj_iter_next(yyjson_mut_obj_iter *iter)
Definition yyjson.h:6906
yyjson_api_inline yyjson_mut_val * yyjson_mut_obj_iter_remove(yyjson_mut_obj_iter *iter)
Definition yyjson.h:6923
yyjson_api_inline yyjson_mut_val * yyjson_mut_obj_iter_get_val(yyjson_mut_val *key)
Definition yyjson.h:6918
yyjson_api_inline yyjson_mut_obj_iter yyjson_mut_obj_iter_with(yyjson_mut_val *obj)
Definition yyjson.h:6895
示例代码2(可变foreach宏):
size_t idx, max;
your_func(key, val);
}
创建JSON文档
yyjson_mut_doc及相关API用于构建JSON文档。
请注意,yyjson_mut_doc使用**内存池**来保存所有字符串和值。内存池只能作为一个整体被创建、扩展或释放。因此,yyjson_mut_doc更适合一次性写入,而不是对现有文档进行修改。
JSON对象和数组由链表组成,因此每个yyjson_mut_val只能被添加到一个对象或数组中。
示例代码:
yyjson_api_inline yyjson_mut_val * yyjson_mut_obj(yyjson_mut_doc *doc)
Definition yyjson.h:6972
yyjson_api void yyjson_mut_doc_free(yyjson_mut_doc *doc)
yyjson_api_inline yyjson_mut_val * yyjson_mut_int(yyjson_mut_doc *doc, int64_t num)
Definition yyjson.h:6137
yyjson_api_inline bool yyjson_mut_obj_add(yyjson_mut_val *obj, yyjson_mut_val *key, yyjson_mut_val *val)
Definition yyjson.h:7126
yyjson_api_inline bool yyjson_mut_arr_append(yyjson_mut_val *arr, yyjson_mut_val *val)
Definition yyjson.h:6507
可变文档
以下函数用于创建、修改、复制和销毁JSON文档。
yyjson_api yyjson_mut_val * yyjson_mut_val_mut_copy(yyjson_mut_doc *doc, yyjson_mut_val *val)
yyjson_api yyjson_mut_doc * yyjson_mut_doc_mut_copy(yyjson_mut_doc *doc, const yyjson_alc *alc)
yyjson_api bool yyjson_mut_doc_set_val_pool_size(yyjson_mut_doc *doc, size_t count)
yyjson_api_inline yyjson_mut_val * yyjson_mut_doc_get_root(yyjson_mut_doc *doc)
Definition yyjson.h:5803
yyjson_api bool yyjson_mut_doc_set_str_pool_size(yyjson_mut_doc *doc, size_t len)
JSON值创建
以下函数用于创建可变JSON值,值的内存由文档持有。
yyjson_api_inline yyjson_mut_val * yyjson_mut_true(yyjson_mut_doc *doc)
Definition yyjson.h:6114
yyjson_api_inline yyjson_mut_val * yyjson_mut_real(yyjson_mut_doc *doc, double num)
Definition yyjson.h:6152
yyjson_api_inline yyjson_mut_val * yyjson_mut_false(yyjson_mut_doc *doc)
Definition yyjson.h:6118
yyjson_api_inline yyjson_mut_val * yyjson_mut_float(yyjson_mut_doc *doc, float num)
Definition yyjson.h:6142
yyjson_api_inline yyjson_mut_val * yyjson_mut_bool(yyjson_mut_doc *doc, bool val)
Definition yyjson.h:6122
yyjson_api_inline yyjson_mut_val * yyjson_mut_null(yyjson_mut_doc *doc)
Definition yyjson.h:6110
yyjson_api_inline yyjson_mut_val * yyjson_mut_uint(yyjson_mut_doc *doc, uint64_t num)
Definition yyjson.h:6127
yyjson_api_inline yyjson_mut_val * yyjson_mut_double(yyjson_mut_doc *doc, double num)
Definition yyjson.h:6147
yyjson_api_inline yyjson_mut_val * yyjson_mut_sint(yyjson_mut_doc *doc, int64_t num)
Definition yyjson.h:6132
JSON数组创建
以下函数用于创建可变JSON数组。
int vals[3] = {-1, 0, 1};
const char strs[3] = {"Jan", "Feb", "Mar"};
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_sint(yyjson_mut_doc *doc, const int64_t *vals, size_t count)
Definition yyjson.h:6335
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_uint8(yyjson_mut_doc *doc, const uint8_t *vals, size_t count)
Definition yyjson.h:6380
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_sint64(yyjson_mut_doc *doc, const int64_t *vals, size_t count)
Definition yyjson.h:6373
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_strn(yyjson_mut_doc *doc, const char **vals, const size_t *lens, size_t count)
Definition yyjson.h:6430
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_float(yyjson_mut_doc *doc, const float *vals, size_t count)
Definition yyjson.h:6408
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_sint32(yyjson_mut_doc *doc, const int32_t *vals, size_t count)
Definition yyjson.h:6366
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_real(yyjson_mut_doc *doc, const double *vals, size_t count)
Definition yyjson.h:6345
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_sint16(yyjson_mut_doc *doc, const int16_t *vals, size_t count)
Definition yyjson.h:6359
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_uint16(yyjson_mut_doc *doc, const uint16_t *vals, size_t count)
Definition yyjson.h:6387
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_strcpy(yyjson_mut_doc *doc, const char **vals, size_t count)
Definition yyjson.h:6439
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_uint64(yyjson_mut_doc *doc, const uint64_t *vals, size_t count)
Definition yyjson.h:6401
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_uint(yyjson_mut_doc *doc, const uint64_t *vals, size_t count)
Definition yyjson.h:6340
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_sint8(yyjson_mut_doc *doc, const int8_t *vals, size_t count)
Definition yyjson.h:6352
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_uint32(yyjson_mut_doc *doc, const uint32_t *vals, size_t count)
Definition yyjson.h:6394
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_double(yyjson_mut_doc *doc, const double *vals, size_t count)
Definition yyjson.h:6415
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_strncpy(yyjson_mut_doc *doc, const char **vals, const size_t *lens, size_t count)
Definition yyjson.h:6453
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_str(yyjson_mut_doc *doc, const char **vals, size_t count)
Definition yyjson.h:6422
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_with_bool(yyjson_mut_doc *doc, const bool *vals, size_t count)
Definition yyjson.h:6328
JSON数组修改
以下函数用于修改JSON数组的内容。
yyjson_api_inline bool yyjson_mut_arr_add_str(yyjson_mut_doc *doc, yyjson_mut_val *arr, const char *str)
Definition yyjson.h:6788
yyjson_api_inline bool yyjson_mut_arr_add_true(yyjson_mut_doc *doc, yyjson_mut_val *arr)
Definition yyjson.h:6700
yyjson_api_inline bool yyjson_mut_arr_prepend(yyjson_mut_val *arr, yyjson_mut_val *val)
Definition yyjson.h:6526
yyjson_api_inline bool yyjson_mut_arr_add_strncpy(yyjson_mut_doc *doc, yyjson_mut_val *arr, const char *str, size_t len)
Definition yyjson.h:6818
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_remove(yyjson_mut_val *arr, size_t idx)
Definition yyjson.h:6573
yyjson_api_inline bool yyjson_mut_arr_clear(yyjson_mut_val *arr)
Definition yyjson.h:6660
yyjson_api_inline bool yyjson_mut_arr_add_strcpy(yyjson_mut_doc *doc, yyjson_mut_val *arr, const char *str)
Definition yyjson.h:6808
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_replace(yyjson_mut_val *arr, size_t idx, yyjson_mut_val *val)
Definition yyjson.h:6545
yyjson_api_inline bool yyjson_mut_arr_add_double(yyjson_mut_doc *doc, yyjson_mut_val *arr, double num)
Definition yyjson.h:6768
yyjson_api_inline bool yyjson_mut_arr_add_bool(yyjson_mut_doc *doc, yyjson_mut_val *arr, bool val)
Definition yyjson.h:6718
yyjson_api_inline bool yyjson_mut_arr_add_uint(yyjson_mut_doc *doc, yyjson_mut_val *arr, uint64_t num)
Definition yyjson.h:6728
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_add_arr(yyjson_mut_doc *doc, yyjson_mut_val *arr)
Definition yyjson.h:6828
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_remove_last(yyjson_mut_val *arr)
Definition yyjson.h:6616
yyjson_api_inline bool yyjson_mut_arr_add_false(yyjson_mut_doc *doc, yyjson_mut_val *arr)
Definition yyjson.h:6709
yyjson_api_inline bool yyjson_mut_arr_add_strn(yyjson_mut_doc *doc, yyjson_mut_val *arr, const char *str, size_t len)
Definition yyjson.h:6798
yyjson_api_inline bool yyjson_mut_arr_add_real(yyjson_mut_doc *doc, yyjson_mut_val *arr, double num)
Definition yyjson.h:6778
yyjson_api_inline bool yyjson_mut_arr_add_float(yyjson_mut_doc *doc, yyjson_mut_val *arr, float num)
Definition yyjson.h:6758
yyjson_api_inline bool yyjson_mut_arr_add_val(yyjson_mut_val *arr, yyjson_mut_val *val)
Definition yyjson.h:6686
yyjson_api_inline bool yyjson_mut_arr_add_sint(yyjson_mut_doc *doc, yyjson_mut_val *arr, int64_t num)
Definition yyjson.h:6738
yyjson_api_inline bool yyjson_mut_arr_remove_range(yyjson_mut_val *arr, size_t idx, size_t len)
Definition yyjson.h:6638
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_add_obj(yyjson_mut_doc *doc, yyjson_mut_val *arr)
Definition yyjson.h:6837
yyjson_api_inline bool yyjson_mut_arr_insert(yyjson_mut_val *arr, yyjson_mut_val *val, size_t idx)
Definition yyjson.h:6476
yyjson_api_inline yyjson_mut_val * yyjson_mut_arr_remove_first(yyjson_mut_val *arr)
Definition yyjson.h:6597
yyjson_api_inline bool yyjson_mut_arr_add_null(yyjson_mut_doc *doc, yyjson_mut_val *arr)
Definition yyjson.h:6691
JSON对象创建
以下函数用于创建可变JSON对象。
const char **keys,
const char **vals,
size_t count);
const char keys[] = {"name", "type", "id"};
const char *vals[] = {"Harry", "student", "123456"};
const char **kv_pairs,
size_t pair_count);
const char *pairs[] = {"name", "Harry", "type", "student", "id", "123456"};
yyjson_api_inline yyjson_mut_val * yyjson_mut_obj_with_str(yyjson_mut_doc *doc, const char **keys, const char **vals, size_t count)
Definition yyjson.h:6983
yyjson_api_inline yyjson_mut_val * yyjson_mut_obj_with_kv(yyjson_mut_doc *doc, const char **kv_pairs, size_t pair_count)
Definition yyjson.h:7014
JSON对象修改
以下函数用于修改JSON对象的内容。
yyjson_api_inline yyjson_mut_val * yyjson_mut_obj_add_arr(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key)
Definition yyjson.h:7383
yyjson_api_inline bool yyjson_mut_obj_add_strncpy(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key, const char *val, size_t len)
Definition yyjson.h:7370
yyjson_api_inline bool yyjson_mut_obj_add_double(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key, double val)
Definition yyjson.h:7317
yyjson_api_inline bool yyjson_mut_obj_rename_keyn(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key, size_t len, const char *new_key, size_t new_len)
Definition yyjson.h:7441
yyjson_api_inline bool yyjson_mut_obj_add_sint(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key, int64_t val)
Definition yyjson.h:7296
yyjson_api_inline bool yyjson_mut_obj_add_strn(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key, const char *val, size_t len)
Definition yyjson.h:7345
yyjson_api_inline bool yyjson_mut_obj_add_false(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key)
Definition yyjson.h:7276
yyjson_api_inline bool yyjson_mut_obj_add_int(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key, int64_t val)
Definition yyjson.h:7303
yyjson_api_inline bool yyjson_mut_obj_add_uint(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key, uint64_t val)
Definition yyjson.h:7289
yyjson_api_inline yyjson_mut_val * yyjson_mut_obj_remove_str(yyjson_mut_val *obj, const char *key)
Definition yyjson.h:7409
yyjson_api_inline yyjson_mut_val * yyjson_mut_obj_remove(yyjson_mut_val *obj, yyjson_mut_val *key)
Definition yyjson.h:7185
#define yyjson_api_inline
Definition yyjson.h:343
yyjson_api_inline bool yyjson_mut_obj_add_null(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key)
Definition yyjson.h:7264
yyjson_api_inline yyjson_mut_val * yyjson_mut_obj_add_obj(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key)
Definition yyjson.h:7391
yyjson_api_inline bool yyjson_mut_obj_add_true(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key)
Definition yyjson.h:7270
yyjson_api_inline bool yyjson_mut_obj_add_str(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key, const char *val)
Definition yyjson.h:7331
yyjson_api_inline bool yyjson_mut_obj_add_real(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key, double val)
Definition yyjson.h:7324
yyjson_api_inline bool yyjson_mut_obj_add_bool(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key, bool val)
Definition yyjson.h:7282
yyjson_api_inline bool yyjson_mut_obj_add_strcpy(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key, const char *val)
Definition yyjson.h:7357
yyjson_api_inline bool yyjson_mut_obj_put(yyjson_mut_val *obj, yyjson_mut_val *key, yyjson_mut_val *val)
Definition yyjson.h:7137
yyjson_api_inline yyjson_mut_val * yyjson_mut_obj_remove_strn(yyjson_mut_val *obj, const char *key, size_t len)
Definition yyjson.h:7414
yyjson_api_inline bool yyjson_mut_obj_rename_key(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key, const char *new_key)
Definition yyjson.h:7432
yyjson_api_inline bool yyjson_mut_obj_add_float(yyjson_mut_doc *doc, yyjson_mut_val *obj, const char *key, float val)
Definition yyjson.h:7310
yyjson_api_inline bool yyjson_mut_obj_clear(yyjson_mut_val *obj)
Definition yyjson.h:7211
JSON Pointer和Patch
JSON Pointer
本库支持使用JSON Pointer(RFC 6901)查询JSON值。
yyjson_api_inline yyjson_mut_val * yyjson_mut_doc_ptr_getn(yyjson_mut_doc *doc, const char *ptr, size_t len)
Definition yyjson.h:7581
yyjson_api_inline yyjson_val * yyjson_ptr_getx(yyjson_val *val, const char *ptr, size_t len, yyjson_ptr_err *err)
Definition yyjson.h:7557
yyjson_api_inline yyjson_val * yyjson_doc_ptr_getx(yyjson_doc *doc, const char *ptr, size_t len, yyjson_ptr_err *err)
Definition yyjson.h:7524
yyjson_api_inline yyjson_mut_val * yyjson_mut_doc_ptr_get(yyjson_mut_doc *doc, const char *ptr)
Definition yyjson.h:7575
yyjson_api_inline yyjson_val * yyjson_doc_ptr_getn(yyjson_doc *doc, const char *ptr, size_t len)
Definition yyjson.h:7519
yyjson_api_inline yyjson_mut_val * yyjson_mut_doc_ptr_getx(yyjson_mut_doc *doc, const char *ptr, size_t len, yyjson_ptr_ctx *ctx, yyjson_ptr_err *err)
Definition yyjson.h:7587
yyjson_api_inline yyjson_mut_val * yyjson_mut_ptr_getn(yyjson_mut_val *val, const char *ptr, size_t len)
Definition yyjson.h:7619
yyjson_api_inline yyjson_val * yyjson_ptr_get(yyjson_val *val, const char *ptr)
Definition yyjson.h:7546
yyjson_api_inline yyjson_mut_val * yyjson_mut_ptr_get(yyjson_mut_val *val, const char *ptr)
Definition yyjson.h:7613
yyjson_api_inline yyjson_val * yyjson_doc_ptr_get(yyjson_doc *doc, const char *ptr)
Definition yyjson.h:7513
yyjson_api_inline yyjson_val * yyjson_ptr_getn(yyjson_val *val, const char *ptr, size_t len)
Definition yyjson.h:7552
yyjson_api_inline yyjson_mut_val * yyjson_mut_ptr_getx(yyjson_mut_val *val, const char *ptr, size_t len, yyjson_ptr_ctx *ctx, yyjson_ptr_err *err)
Definition yyjson.h:7625
例如,给定以下JSON文档:
{
"size" : 3,
"users" : [
{"id": 1, "name": "Harry"},
{"id": 2, "name": "Ron"},
{"id": 3, "name": "Hermione"}
]
}
以下JSON字符串将解析为对应的值:
| 指针 | 匹配的值 |
"" | 整个文档 |
"/size" | 3 |
"/users/0" | {"id": 1, "name": "Harry"} |
"/users/1/name" | "Ron" |
"/no_match" | NULL |
"no_slash" | NULL |
"/" | NULL(匹配空键:root[""]) |
if (!val2) printf(
"错误 %d: %s\n", err.
code, err.
msg);
const char * msg
Definition yyjson.h:4198
yyjson_ptr_code code
Definition yyjson.h:4196
本库还支持使用JSON Pointer修改JSON值。
yyjson_api_inline yyjson_mut_val * yyjson_mut_doc_ptr_remove(yyjson_mut_doc *doc, const char *ptr)
Definition yyjson.h:7933
yyjson_api_inline bool yyjson_mut_ptr_setx(yyjson_mut_val *val, const char *ptr, size_t len, yyjson_mut_val *new_val, yyjson_mut_doc *doc, bool create_parent, yyjson_ptr_ctx *ctx, yyjson_ptr_err *err)
Definition yyjson.h:7827
yyjson_api_inline yyjson_mut_val * yyjson_mut_doc_ptr_replace(yyjson_mut_doc *doc, const char *ptr, yyjson_mut_val *new_val)
Definition yyjson.h:7856
yyjson_api_inline bool yyjson_mut_doc_ptr_setn(yyjson_mut_doc *doc, const char *ptr, size_t len, yyjson_mut_val *new_val)
Definition yyjson.h:7756
yyjson_api_inline bool yyjson_mut_ptr_addx(yyjson_mut_val *val, const char *ptr, size_t len, yyjson_mut_val *new_val, yyjson_mut_doc *doc, bool create_parent, yyjson_ptr_ctx *ctx, yyjson_ptr_err *err)
Definition yyjson.h:7723
yyjson_api_inline yyjson_mut_val * yyjson_mut_doc_ptr_removex(yyjson_mut_doc *doc, const char *ptr, size_t len, yyjson_ptr_ctx *ctx, yyjson_ptr_err *err)
Definition yyjson.h:7944
yyjson_api_inline yyjson_mut_val * yyjson_mut_ptr_removen(yyjson_mut_val *val, const char *ptr, size_t len)
Definition yyjson.h:7978
yyjson_api_inline yyjson_mut_val * yyjson_mut_ptr_replacex(yyjson_mut_val *val, const char *ptr, size_t len, yyjson_mut_val *new_val, yyjson_ptr_ctx *ctx, yyjson_ptr_err *err)
Definition yyjson.h:7911
yyjson_api_inline bool yyjson_mut_doc_ptr_setx(yyjson_mut_doc *doc, const char *ptr, size_t len, yyjson_mut_val *new_val, bool create_parent, yyjson_ptr_ctx *ctx, yyjson_ptr_err *err)
Definition yyjson.h:7762
yyjson_api_inline bool yyjson_mut_ptr_set(yyjson_mut_val *val, const char *ptr, yyjson_mut_val *new_val, yyjson_mut_doc *doc)
Definition yyjson.h:7812
yyjson_api_inline yyjson_mut_val * yyjson_mut_doc_ptr_removen(yyjson_mut_doc *doc, const char *ptr, size_t len)
Definition yyjson.h:7939
yyjson_api_inline bool yyjson_mut_doc_ptr_addn(yyjson_mut_doc *doc, const char *ptr, size_t len, yyjson_mut_val *new_val)
Definition yyjson.h:7654
yyjson_api_inline yyjson_mut_val * yyjson_mut_ptr_removex(yyjson_mut_val *val, const char *ptr, size_t len, yyjson_ptr_ctx *ctx, yyjson_ptr_err *err)
Definition yyjson.h:7984
yyjson_api_inline bool yyjson_mut_doc_ptr_set(yyjson_mut_doc *doc, const char *ptr, yyjson_mut_val *new_val)
Definition yyjson.h:7749
yyjson_api_inline yyjson_mut_val * yyjson_mut_doc_ptr_replacen(yyjson_mut_doc *doc, const char *ptr, size_t len, yyjson_mut_val *new_val)
Definition yyjson.h:7862
yyjson_api_inline yyjson_mut_val * yyjson_mut_ptr_remove(yyjson_mut_val *val, const char *ptr)
Definition yyjson.h:7972
yyjson_api_inline bool yyjson_mut_ptr_addn(yyjson_mut_val *val, const char *ptr, size_t len, yyjson_mut_val *new_val, yyjson_mut_doc *doc)
Definition yyjson.h:7716
yyjson_api_inline bool yyjson_mut_ptr_add(yyjson_mut_val *val, const char *ptr, yyjson_mut_val *new_val, yyjson_mut_doc *doc)
Definition yyjson.h:7708
yyjson_api_inline bool yyjson_mut_ptr_setn(yyjson_mut_val *val, const char *ptr, size_t len, yyjson_mut_val *new_val, yyjson_mut_doc *doc)
Definition yyjson.h:7820
yyjson_api_inline bool yyjson_mut_doc_ptr_addx(yyjson_mut_doc *doc, const char *ptr, size_t len, yyjson_mut_val *new_val, bool create_parent, yyjson_ptr_ctx *ctx, yyjson_ptr_err *err)
Definition yyjson.h:7661
yyjson_api_inline yyjson_mut_val * yyjson_mut_ptr_replace(yyjson_mut_val *val, const char *ptr, yyjson_mut_val *new_val)
Definition yyjson.h:7900
yyjson_api_inline bool yyjson_mut_doc_ptr_add(yyjson_mut_doc *doc, const char *ptr, yyjson_mut_val *new_val)
Definition yyjson.h:7647
yyjson_api_inline yyjson_mut_val * yyjson_mut_doc_ptr_replacex(yyjson_mut_doc *doc, const char *ptr, size_t len, yyjson_mut_val *new_val, yyjson_ptr_ctx *ctx, yyjson_ptr_err *err)
Definition yyjson.h:7867
yyjson_api_inline yyjson_mut_val * yyjson_mut_ptr_replacen(yyjson_mut_val *val, const char *ptr, size_t len, yyjson_mut_val *new_val)
Definition yyjson.h:7906
例如:
所有以x结尾的上述函数可用于获取结果上下文ctx和错误信息err。例如:
if (err.
code) printf(
"错误: %s\n", err.
msg);
yyjson_api_inline bool yyjson_mut_is_null(yyjson_mut_val *val)
Definition yyjson.h:5822
yyjson_api_inline bool yyjson_ptr_ctx_remove(yyjson_ptr_ctx *ctx)
Definition yyjson.h:8093
JSON Patch
本库支持JSON Patch(RFC 6902)。 规范和示例:https://tools.ietf.org/html/rfc6902
yyjson_api yyjson_mut_val * yyjson_patch(yyjson_mut_doc *doc, yyjson_val *orig, yyjson_val *patch, yyjson_patch_err *err)
yyjson_api yyjson_mut_val * yyjson_mut_patch(yyjson_mut_doc *doc, yyjson_mut_val *orig, yyjson_mut_val *patch, yyjson_patch_err *err)
JSON Merge Patch
本库支持JSON Merge Patch(RFC 7386)。 规范和示例:https://tools.ietf.org/html/rfc7386
yyjson_api yyjson_mut_val * yyjson_merge_patch(yyjson_mut_doc *doc, yyjson_val *orig, yyjson_val *patch)
yyjson_api yyjson_mut_val * yyjson_mut_merge_patch(yyjson_mut_doc *doc, yyjson_mut_val *orig, yyjson_mut_val *patch)
数字处理
数字读取器
本库内置高性能数字读取器,
默认情况下,它将按以下规则读取数字:
- 正整数被读取为
uint64_t。如果发生溢出,则转换为double。
- 负整数被读取为
int64_t。如果发生溢出,则转换为double。
- 浮点数被正确四舍五入后读取为
double。
- 如果
double数值溢出(达到无穷大),则报告错误。
- 如果数字不符合JSON标准,则报告错误。
有3个标志可用于调整数字解析策略:
YYJSON_READ_ALLOW_INF_AND_NAN:将nan/inf数字或字面量读取为double(非标准)。
YYJSON_READ_NUMBER_AS_RAW:将所有数字作为原始字符串读取而不进行解析。
YYJSON_READ_BIGNUM_AS_RAW:将大数(溢出或无穷大)作为原始字符串读取而不进行解析。
详见读取器标志章节。
数字写出器
本库内置高性能数字写出器,
默认情况下,它将按以下规则写出数字:
- 正整数不带符号写出。
- 负整数带负号写出。
- 浮点数使用ECMAScript格式写出,但有以下修改:
- 如果数字是
Infinity或NaN,则报告错误。
- 保留
-0.0的负号以保持输入信息。
- 移除指数部分的正号。
- 浮点数写出器将生成最短的、正确四舍五入的十进制表示。
有几个标志可用于调整数字写出策略:
YYJSON_WRITE_ALLOW_INF_AND_NAN:将inf/nan数字写为Infinity和NaN字面量而不报错(非标准)。
YYJSON_WRITE_INF_AND_NAN_AS_NULL:将inf/nan数字写为null字面量。
YYJSON_WRITE_FP_TO_FLOAT:将实数写为float而非double。
YYJSON_WRITE_FP_TO_FIXED(prec):使用定点表示法写出实数。
详见写出器标志章节。
还有一些辅助函数可用于控制单个值的输出格式:
数字转换函数
还有两个工具函数可直接访问库内部的数字转换逻辑。 它们用于独立使用,通常不分配内存。
yyjson_api char * yyjson_write_number(const yyjson_val *val, char *buf)
yyjson_api const char * yyjson_read_number(const char *dat, yyjson_val *val, yyjson_read_flag flg, const yyjson_alc *alc, yyjson_read_err *err)
文本处理
字符编码
默认情况下,本库支持不带BOM的UTF-8编码,如RFC 8259所规定:
在不属于封闭生态系统的系统之间交换的JSON文本必须使用UTF-8编码。 实现不得在网络传输的JSON文本开头添加字节顺序标记(U+FEFF)。
本库默认对输入字符串执行严格的UTF-8编码验证。如果遇到无效字符,将报告错误。
要允许BOM,请使用YYJSON_READ_ALLOW_BOM或YYJSON_READ_ALLOW_EXT_WHITESPACE标志。
要允许无效的Unicode编码,请使用YYJSON_READ_ALLOW_INVALID_UNICODE和YYJSON_WRITE_ALLOW_INVALID_UNICODE标志。**注意:** 启用这些标志可能会导致yyjson生成包含无效字符的值,这些值可能被其他代码处理并引入安全风险。
要将字符串标记为在JSON写出时不需要转义,请使用yyjson_set_str_noesc(yyjson_val *val, bool noesc)或yyjson_mut_set_str_noesc(yyjson_mut_val *val, bool noesc)。这可以提高字符串写出性能并保留原始字符串字节。
NUL字符
本库支持字符串中的NUL字符(也称为空终止符,或Unicode U+0000,ASCII \0)。
读取JSON时,\u0000将被转义为NUL字符。如果字符串包含NUL字符,使用strlen()获取的长度将不准确,你应该使用yyjson_get_len()获取实际长度。
构建JSON时,输入字符串默认被视为以空终止符结尾。如果需要传入包含NUL字符的字符串,应该使用带n后缀的API并提供字符串的实际长度。
例如:
内存分配器
本库不直接调用libc的内存分配函数(malloc/realloc/free)。相反,当需要内存分配时,yyjson的API接受一个名为alc的参数,允许调用者传入分配器。如果alc为NULL,yyjson将使用默认内存分配器,这是libc函数的简单封装。
使用自定义内存分配器可以让你更好地控制内存分配,以下是几个示例:
多个JSON共用单一分配器
如果你需要逐个解析多个小型JSON,可以使用单一分配器来避免多次内存分配。
示例代码:
size_t max_json_size = 64 * 1024;
void *buf = malloc(buf_size);
for(int i = 0, i < your_json_file_count; i++) {
const char *your_json_file_path = ...;
...
}
free(buf);
yyjson_api_inline size_t yyjson_read_max_memory_usage(size_t len, yyjson_read_flag flg)
Definition yyjson.h:1096
如果你不确定处理JSON所需的内存量,可以使用动态分配器。
for(int i = 0, i < your_json_file_count; i++) {
const char *your_json_file_path = ...;
...
}
yyjson_api yyjson_alc * yyjson_alc_dyn_new(void)
yyjson_api void yyjson_alc_dyn_free(yyjson_alc *alc)
栈内存分配器
如果JSON足够小,可以使用栈内存来读取或写入。
示例代码:
char buf[128 * 1024];
...
yyjson_doc_free(doc);
使用第三方分配器库
你可以为yyjson使用第三方高性能内存分配器,例如jemalloc、tcmalloc、mimalloc。你也可以参考以下代码实现自己的分配器。
示例代码:
#include <mimalloc.h>
static void *priv_malloc(void *ctx, size_t size) {
return mi_malloc(size);
}
static void *priv_realloc(void *ctx, void *ptr, size_t old_size, size_t size) {
return mi_realloc(ptr, size);
}
static void priv_free(void *ctx, void *ptr) {
mi_free(ptr);
}
priv_malloc,
priv_realloc,
priv_free,
NULL
};
yyjson_doc *doc = yyjson_doc_read_opts(dat, len, 0, &PRIV_ALC, NULL);
...
yyjson_doc_free(doc);
char *json = yyjson_doc_write(doc, 0, alc, NULL, NULL);
...
alc->free(alc->
ctx, json);
栈内存使用
本库中的大多数函数都使用固定大小的栈内存。这包括JSON读写函数以及JSON Pointer处理函数。
然而,有少数函数使用了递归,如果嵌套层级过深可能会导致栈溢出。这些函数在头文件中会用以下警告标记:
- Warning
- 本函数使用了递归,如果对象层级过深可能会导致栈溢出。
空值检查
本库的公共API会对每个输入参数执行空值检查以防止程序崩溃。
例如,在读取JSON时,你就不需要亲自对每个值进行空值检查或类型检查:
if (!str) printf("err!");
然而,如果你十分确定某个值非空且为符合预期的类型,可以使用带有unsafe前缀的API来跳过空值检查。
例如,在遍历数组或对象时,值和键必定非空:
size_t idx, max;
if (unsafe_yyjson_equals_str(key, "id") &&
unsafe_yyjson_is_uint(val) &&
unsafe_yyjson_get_uint(val) == 1234) {
...
}
}
线程安全
本库不使用全局变量。因此如果你能确保输入函数的实参是线程安全的,那么函数调用就也是线程安全的。
一般来说,yyjson_doc和yyjson_val是不可变的且线程安全的,而yyjson_mut_doc和yyjson_mut_val是可变的且非线程安全的。
区域设置独立性
本库设计上是区域设置无关的。(译者注:库的运行效果和你所处的国家或地区无关)
然而,有一些情况你需要注意避免:
- 当你在代码中使用了libc的
setlocale()函数来更改区域设置。
- 当你的运行环境不遵循IEEE 754浮点数标准(例如某些IBM大型机),或者你在构建时显式设置了
YYJSON_DISABLE_FAST_FP_CONV,在这种情况下yyjson将使用strtod()来解析浮点数。
如果**同时**满足这两个条件,请避免在某个线程正在解析JSON时调用setlocale()。否则当解析到JSON中的浮点数时可能会返回错误。