gojay

high performance JSON encoder/decoder with stream API for Golang
git clone git://git.lair.cx/gojay
Log | Files | Refs | README | LICENSE

commit 820044ef83b5f70f7bedd63b2c1bdbe6b30c848e
parent 7a565adc8b519c6b40a3016bea655a24261bcc90
Author: francoispqt <francois@parquet.ninja>
Date:   Mon,  7 May 2018 20:57:09 +0800

add int64 funcs to encoder and optimisations

Diffstat:
Mencode_array.go | 6+++---
Mencode_bool.go | 4++--
Mencode_number.go | 40+++++++++++++++++++++++++++++++++++-----
Mencode_number_test.go | 49+++++++++++++++++++++++++++++++++++++++++++++++++
4 files changed, 89 insertions(+), 10 deletions(-)

diff --git a/encode_array.go b/encode_array.go @@ -66,7 +66,7 @@ func (enc *Encoder) AddArrayKey(key string, v MarshalerArray) { if v.IsNil() { enc.grow(2 + len(key)) r := enc.getPreviousRune() - if r != '[' { + if r != '{' { enc.writeByte(',') } enc.writeByte('"') @@ -77,7 +77,7 @@ func (enc *Encoder) AddArrayKey(key string, v MarshalerArray) { } enc.grow(5 + len(key)) r := enc.getPreviousRune() - if r != '[' && r != '{' { + if r != '{' { enc.writeByte(',') } enc.writeByte('"') @@ -95,7 +95,7 @@ func (enc *Encoder) AddArrayKeyOmitEmpty(key string, v MarshalerArray) { } enc.grow(5 + len(key)) r := enc.getPreviousRune() - if r != '[' && r != '{' { + if r != '{' { enc.writeByte(',') } enc.writeByte('"') diff --git a/encode_bool.go b/encode_bool.go @@ -58,7 +58,7 @@ func (enc *Encoder) AddBoolOmitEmpty(v bool) { func (enc *Encoder) AddBoolKey(key string, value bool) { enc.grow(5 + len(key)) r := enc.getPreviousRune() - if r != '{' && r != '[' { + if r != '{' { enc.writeByte(',') } enc.writeByte('"') @@ -75,7 +75,7 @@ func (enc *Encoder) AddBoolKeyOmitEmpty(key string, v bool) { } enc.grow(5 + len(key)) r := enc.getPreviousRune() - if r != '{' && r != '[' { + if r != '{' { enc.writeByte(',') } enc.writeByte('"') diff --git a/encode_number.go b/encode_number.go @@ -152,7 +152,7 @@ func (enc *Encoder) AddFloat32OmitEmpty(v float32) { func (enc *Encoder) AddIntKey(key string, v int) { enc.grow(10 + len(key)) r := enc.getPreviousRune() - if r != '{' && r != '[' { + if r != '{' { enc.writeByte(',') } enc.writeByte('"') @@ -178,10 +178,40 @@ func (enc *Encoder) AddIntKeyOmitEmpty(key string, v int) { enc.buf = strconv.AppendInt(enc.buf, int64(v), 10) } +// AddInt64Key adds an int64 to be encoded, must be used inside an object as it will encode a key +func (enc *Encoder) AddInt64Key(key string, v int64) { + enc.grow(10 + len(key)) + r := enc.getPreviousRune() + if r != '{' { + enc.writeByte(',') + } + enc.writeByte('"') + enc.writeStringEscape(key) + enc.writeBytes(objKey) + enc.buf = strconv.AppendInt(enc.buf, v, 10) +} + +// AddInt64KeyOmitEmpty adds an int64 to be encoded and skips it if its value is 0. +// Must be used inside an object as it will encode a key. +func (enc *Encoder) AddInt64KeyOmitEmpty(key string, v int64) { + if v == 0 { + return + } + enc.grow(10 + len(key)) + r := enc.getPreviousRune() + if r != '{' { + enc.writeByte(',') + } + enc.writeByte('"') + enc.writeStringEscape(key) + enc.writeBytes(objKey) + enc.buf = strconv.AppendInt(enc.buf, v, 10) +} + // AddFloatKey adds a float64 to be encoded, must be used inside an object as it will encode a key func (enc *Encoder) AddFloatKey(key string, value float64) { r := enc.getPreviousRune() - if r != '{' && r != '[' { + if r != '{' { enc.writeByte(',') } enc.grow(10) @@ -199,7 +229,7 @@ func (enc *Encoder) AddFloatKeyOmitEmpty(key string, v float64) { } enc.grow(10 + len(key)) r := enc.getPreviousRune() - if r != '{' && r != '[' { + if r != '{' { enc.writeByte(',') } enc.writeByte('"') @@ -212,7 +242,7 @@ func (enc *Encoder) AddFloatKeyOmitEmpty(key string, v float64) { func (enc *Encoder) AddFloat32Key(key string, v float32) { enc.grow(10 + len(key)) r := enc.getPreviousRune() - if r != '{' && r != '[' { + if r != '{' { enc.writeByte(',') } enc.writeByte('"') @@ -230,7 +260,7 @@ func (enc *Encoder) AddFloat32KeyOmitEmpty(key string, v float32) { } enc.grow(10 + len(key)) r := enc.getPreviousRune() - if r != '{' && r != '[' { + if r != '{' { enc.writeByte(',') } enc.writeByte('"') diff --git a/encode_number_test.go b/encode_number_test.go @@ -227,3 +227,52 @@ func TestEncoderNumberMarshalAPI(t *testing.T) { "Result of marshalling is different as the one expected") }) } + +func TestAddNumberFunc(t *testing.T) { + t.Run("int64", func(t *testing.T) { + builder := &strings.Builder{} + enc := BorrowEncoder(builder) + enc.writeByte('{') + enc.AddInt64Key("test", 10) + _, err := enc.Write() + assert.Nil(t, err, "err should be nil") + assert.Equal(t, `{"test":10`, builder.String(), `builder.String() should be equal to {"test":10"`) + }) + t.Run("int64-2", func(t *testing.T) { + builder := &strings.Builder{} + enc := BorrowEncoder(builder) + enc.writeBytes([]byte(`{"test":1`)) + enc.AddInt64Key("test", 10) + _, err := enc.Write() + assert.Nil(t, err, "err should be nil") + assert.Equal(t, `{"test":1,"test":10`, builder.String(), `builder.String() should be equal to {"test":10"`) + }) + + t.Run("int64-omit-empty", func(t *testing.T) { + builder := &strings.Builder{} + enc := BorrowEncoder(builder) + enc.writeByte('{') + enc.AddInt64KeyOmitEmpty("test", 10) + _, err := enc.Write() + assert.Nil(t, err, "err should be nil") + assert.Equal(t, `{"test":10`, builder.String(), `builder.String() should be equal to {"test":10"`) + }) + t.Run("int64-omit-empty-2", func(t *testing.T) { + builder := &strings.Builder{} + enc := BorrowEncoder(builder) + enc.writeBytes([]byte(`{"test":1`)) + enc.AddInt64KeyOmitEmpty("test", 10) + _, err := enc.Write() + assert.Nil(t, err, "err should be nil") + assert.Equal(t, `{"test":1,"test":10`, builder.String(), `builder.String() should be equal to {"test":10"`) + }) + t.Run("int64-omit-empty-3", func(t *testing.T) { + builder := &strings.Builder{} + enc := BorrowEncoder(builder) + enc.writeByte('{') + enc.AddInt64KeyOmitEmpty("test", 0) + _, err := enc.Write() + assert.Nil(t, err, "err should be nil") + assert.Equal(t, `{`, builder.String(), `builder.String() should be equal to {"test":10"`) + }) +}