faster map unmarshalling

This commit is contained in:
Josh Baker 2016-08-25 20:17:32 -07:00
parent a6e9688393
commit 3913125ac5
1 changed files with 31 additions and 33 deletions

View File

@ -100,8 +100,8 @@ func (t Result) Array() []Result {
if t.Type != JSON { if t.Type != JSON {
return nil return nil
} }
a, _, _, _, _ := t.arrayOrMap('[', false) r := t.arrayOrMap('[', false)
return a return r.a
} }
// Map returns back an map of children. The result should be a JSON array. // Map returns back an map of children. The result should be a JSON array.
@ -109,8 +109,8 @@ func (t Result) Map() map[string]Result {
if t.Type != JSON { if t.Type != JSON {
return map[string]Result{} return map[string]Result{}
} }
_, _, o, _, _ := t.arrayOrMap('{', false) r := t.arrayOrMap('{', false)
return o return r.o
} }
// Get searches result for the specified path. // Get searches result for the specified path.
@ -119,17 +119,15 @@ func (t Result) Get(path string) Result {
return Get(t.Raw, path) return Get(t.Raw, path)
} }
func (t Result) arrayOrMap(vc byte, valueize bool) ( type arrayOrMapResult struct {
[]Result, a []Result
[]interface{}, ai []interface{}
map[string]Result, o map[string]Result
map[string]interface{}, oi map[string]interface{}
byte, vc byte
) { }
var a []Result
var ai []interface{} func (t Result) arrayOrMap(vc byte, valueize bool) (r arrayOrMapResult) {
var o map[string]Result
var oi map[string]interface{}
var json = t.Raw var json = t.Raw
var i int var i int
var value Result var value Result
@ -138,7 +136,7 @@ func (t Result) arrayOrMap(vc byte, valueize bool) (
if vc == 0 { if vc == 0 {
for ; i < len(json); i++ { for ; i < len(json); i++ {
if json[i] == '{' || json[i] == '[' { if json[i] == '{' || json[i] == '[' {
vc = json[i] r.vc = json[i]
i++ i++
break break
} }
@ -156,18 +154,19 @@ func (t Result) arrayOrMap(vc byte, valueize bool) (
goto end goto end
} }
} }
r.vc = vc
} }
if vc == '{' { if r.vc == '{' {
if valueize { if valueize {
oi = make(map[string]interface{}) r.oi = make(map[string]interface{})
} else { } else {
o = make(map[string]Result) r.o = make(map[string]Result)
} }
} else { } else {
if valueize { if valueize {
ai = make([]interface{}, 0) r.ai = make([]interface{}, 0)
} else { } else {
a = make([]Result, 0) r.a = make([]Result, 0)
} }
} }
for ; i < len(json); i++ { for ; i < len(json); i++ {
@ -204,27 +203,27 @@ func (t Result) arrayOrMap(vc byte, valueize bool) (
} }
i += len(value.Raw) - 1 i += len(value.Raw) - 1
if vc == '{' { if r.vc == '{' {
if count%2 == 0 { if count%2 == 0 {
key = value key = value
} else { } else {
if valueize { if valueize {
oi[key.Str] = value.Value() r.oi[key.Str] = value.Value()
} else { } else {
o[key.Str] = value r.o[key.Str] = value
} }
} }
count++ count++
} else { } else {
if valueize { if valueize {
ai = append(ai, value.Value()) r.ai = append(r.ai, value.Value())
} else { } else {
a = append(a, value) r.a = append(r.a, value)
} }
} }
} }
end: end:
return a, ai, o, oi, vc return
} }
// Parse parses the json and returns a result // Parse parses the json and returns a result
@ -417,17 +416,16 @@ func (t Result) Value() interface{} {
case Number: case Number:
return t.Num return t.Num
case JSON: case JSON:
_, ai, _, oi, vc := t.arrayOrMap(0, true) r := t.arrayOrMap(0, true)
if vc == '{' { if r.vc == '{' {
return oi return r.oi
} else if vc == '[' { } else if r.vc == '[' {
return ai return r.ai
} }
return nil return nil
case True: case True:
return true return true
} }
} }
func parseString(json string, i int) (int, string, bool, bool) { func parseString(json string, i int) (int, string, bool, bool) {