jsonparse: A bunch of performance improvements
Turrns out JSON::XS had some pretty good ideas that I could borrow.
This commit is contained in:
parent
ca8d1b72be
commit
ebe84167e7
5 changed files with 144 additions and 111 deletions
24
c/jsonfmt.c
24
c/jsonfmt.c
|
|
@ -30,7 +30,7 @@ static void fujson_fmt_str(pTHX_ fujson_fmt_ctx *ctx, const char *stri, size_t l
|
|||
croak("invalid codepoint encountered in string, cannot format to JSON");
|
||||
}
|
||||
|
||||
fustr_write(&ctx->out, "\"", 1);
|
||||
fustr_write_ch(&ctx->out, '\"');
|
||||
fustr_reserve(&ctx->out, len);
|
||||
|
||||
while (off < len) {
|
||||
|
|
@ -78,7 +78,7 @@ static void fujson_fmt_str(pTHX_ fujson_fmt_ctx *ctx, const char *stri, size_t l
|
|||
}
|
||||
}
|
||||
|
||||
fustr_write(&ctx->out, "\"", 1);
|
||||
fustr_write_ch(&ctx->out, '\"');
|
||||
}
|
||||
|
||||
static const char fujson_digits[] =
|
||||
|
|
@ -109,7 +109,7 @@ static void fujson_fmt_int(pTHX_ fujson_fmt_ctx *ctx, SV *val) {
|
|||
}
|
||||
|
||||
if (uv == 0) {
|
||||
fustr_write(&ctx->out, "0", 1);
|
||||
fustr_write_ch(&ctx->out, '0');
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
@ -125,10 +125,10 @@ static void fujson_fmt_int(pTHX_ fujson_fmt_ctx *ctx, SV *val) {
|
|||
|
||||
static void fujson_fmt_av(pTHX_ fujson_fmt_ctx *ctx, AV *av) {
|
||||
int i, len = av_count(av);
|
||||
fustr_write(&ctx->out, "[", 1);
|
||||
fustr_write_ch(&ctx->out, '[');
|
||||
ctx->pretty++;
|
||||
for (i=0; i<len; i++) {
|
||||
if (i) fustr_write(&ctx->out, ",", 1);
|
||||
if (i) fustr_write_ch(&ctx->out, ',');
|
||||
fujson_fmt_indent(aTHX_ ctx);
|
||||
SV **sv = av_fetch(av, i, 0);
|
||||
if (sv) fujson_fmt(aTHX_ ctx, *sv); /* sv will have magic if av is tied, but fujson_fmt() handles that. */
|
||||
|
|
@ -136,7 +136,7 @@ static void fujson_fmt_av(pTHX_ fujson_fmt_ctx *ctx, AV *av) {
|
|||
}
|
||||
ctx->pretty--;
|
||||
if (i) fujson_fmt_indent(aTHX_ ctx);
|
||||
fustr_write(&ctx->out, "]", 1);
|
||||
fustr_write_ch(&ctx->out, ']');
|
||||
}
|
||||
|
||||
static int fujson_fmt_hvcmp(const void *pa, const void *pb) {
|
||||
|
|
@ -159,12 +159,12 @@ static int fujson_fmt_hvcmp(const void *pa, const void *pb) {
|
|||
|
||||
static void fujson_fmt_hvkv(pTHX_ fujson_fmt_ctx *ctx, HV *hv, HE *he, char **hestr) {
|
||||
STRLEN helen;
|
||||
if (*hestr) fustr_write(&ctx->out, ",", 1);
|
||||
if (*hestr) fustr_write_ch(&ctx->out, ',');
|
||||
fujson_fmt_indent(aTHX_ ctx);
|
||||
*hestr = HePV(he, helen);
|
||||
fujson_fmt_str(aTHX_ ctx, *hestr, helen, HeUTF8(he));
|
||||
if (ctx->pretty > 0) fustr_write(&ctx->out, " : ", 3);
|
||||
else fustr_write(&ctx->out, ":", 1);
|
||||
else fustr_write_ch(&ctx->out, ':');
|
||||
fujson_fmt(aTHX_ ctx, UNLIKELY(SvMAGICAL(hv)) ? hv_iterval(hv, he) : HeVAL(he));
|
||||
}
|
||||
|
||||
|
|
@ -173,7 +173,7 @@ static void fujson_fmt_hv(pTHX_ fujson_fmt_ctx *ctx, HV *hv) {
|
|||
char *hestr = NULL;
|
||||
|
||||
int numkeys = hv_iterinit(hv);
|
||||
fustr_write(&ctx->out, "{", 1);
|
||||
fustr_write_ch(&ctx->out, '{');
|
||||
ctx->pretty++;
|
||||
|
||||
/* Canonical order on tied hashes is not supported. Cpanel::JSON::XS has
|
||||
|
|
@ -204,7 +204,7 @@ static void fujson_fmt_hv(pTHX_ fujson_fmt_ctx *ctx, HV *hv) {
|
|||
}
|
||||
ctx->pretty--;
|
||||
if (hestr) fujson_fmt_indent(aTHX_ ctx);
|
||||
fustr_write(&ctx->out, "}", 1);
|
||||
fustr_write_ch(&ctx->out, '}');
|
||||
}
|
||||
|
||||
static void fujson_fmt_obj(pTHX_ fujson_fmt_ctx *ctx, SV *rv, SV *obj) {
|
||||
|
|
@ -305,9 +305,9 @@ static SV *fujson_fmt_xs(pTHX_ I32 ax, I32 argc, SV *val) {
|
|||
if (ctx.out.maxlen == 0) ctx.out.maxlen = 1<<30;
|
||||
if (ctx.depth == 0) ctx.depth = 512;
|
||||
|
||||
fustr_init(&ctx.out, sv_2mortal(newSV(128)), ctx.out.maxlen);
|
||||
fustr_init(&ctx.out, sv_newmortal(), ctx.out.maxlen);
|
||||
fujson_fmt(aTHX_ &ctx, val);
|
||||
if (ctx.pretty >= 0) fustr_write(&ctx.out, "\n", 1);
|
||||
if (ctx.pretty >= 0) fustr_write_ch(&ctx.out, '\n');
|
||||
r = fustr_done(&ctx.out);
|
||||
if (!encutf8) SvUTF8_on(r);
|
||||
return r;
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue