From 5d7556ad3d556e09fce30c5645eb63692d7921bf Mon Sep 17 00:00:00 2001 From: tidwall Date: Sat, 16 Feb 2019 14:50:53 -0700 Subject: [PATCH] Valid json optimization Added ~20% performance boost be removing extra allocation when Valid() is called with a json string. --- gjson.go | 2 +- gjson_gae.go | 4 ++++ gjson_ngae.go | 8 ++++++++ gjson_test.go | 20 ++++++++++++++++++++ 4 files changed, 33 insertions(+), 1 deletion(-) diff --git a/gjson.go b/gjson.go index 2c9325f..7722ad9 100644 --- a/gjson.go +++ b/gjson.go @@ -2038,7 +2038,7 @@ func validnull(data []byte, i int) (outi int, ok bool) { // value := gjson.Get(json, "name.last") // func Valid(json string) bool { - _, ok := validpayload([]byte(json), 0) + _, ok := validpayload(stringBytes(json), 0) return ok } diff --git a/gjson_gae.go b/gjson_gae.go index 3a2b251..6a316e5 100644 --- a/gjson_gae.go +++ b/gjson_gae.go @@ -8,3 +8,7 @@ func getBytes(json []byte, path string) Result { func fillIndex(json string, c *parseContext) { // noop. Use zero for the Index value. } + +func stringBytes(s string) []byte { + return []byte(s) +} diff --git a/gjson_ngae.go b/gjson_ngae.go index 59e944b..f606581 100644 --- a/gjson_ngae.go +++ b/gjson_ngae.go @@ -67,3 +67,11 @@ func fillIndex(json string, c *parseContext) { } } } + +func stringBytes(s string) []byte { + return *(*[]byte)(unsafe.Pointer(&reflect.SliceHeader{ + Data: (*reflect.StringHeader)(unsafe.Pointer(&s)).Data, + Len: len(s), + Cap: len(s), + })) +} diff --git a/gjson_test.go b/gjson_test.go index 31bd31f..d718ba0 100644 --- a/gjson_test.go +++ b/gjson_test.go @@ -1431,3 +1431,23 @@ func TestArrayValues(t *testing.T) { } } + +func BenchmarkValid(b *testing.B) { + for i := 0; i < b.N; i++ { + Valid(complicatedJSON) + } +} + +func BenchmarkValidBytes(b *testing.B) { + complicatedJSON := []byte(complicatedJSON) + for i := 0; i < b.N; i++ { + ValidBytes(complicatedJSON) + } +} + +func BenchmarkGoStdlibValidBytes(b *testing.B) { + complicatedJSON := []byte(complicatedJSON) + for i := 0; i < b.N; i++ { + json.Valid(complicatedJSON) + } +}