فهرست منبع

array/object to bool/int

Tao Wen 8 سال پیش
والد
کامیت
94ae645ab9
4فایلهای تغییر یافته به همراه114 افزوده شده و 14 حذف شده
  1. 48 6
      feature_any_array.go
  2. 54 8
      feature_any_object.go
  3. 2 0
      jsoniter_array_test.go
  4. 10 0
      jsoniter_object_test.go

+ 48 - 6
feature_any_array.go

@@ -26,6 +26,9 @@ func (any *arrayLazyAny) fillCacheUntil(target int) Any {
 		}
 		return any.cache[target]
 	}
+	if any.cache == nil {
+		any.cache = make([]Any, 0, 8)
+	}
 	i := len(any.cache)
 	if target < i {
 		return any.cache[target]
@@ -65,6 +68,9 @@ func (any *arrayLazyAny) fillCache() {
 	if any.remaining == nil {
 		return
 	}
+	if any.cache == nil {
+		any.cache = make([]Any, 0, 8)
+	}
 	iter := any.parse()
 	if len(any.remaining) == len(any.buf) {
 		iter.head++
@@ -89,27 +95,60 @@ func (any *arrayLazyAny) LastError() error {
 }
 
 func (any *arrayLazyAny) ToBool() bool {
-	return false
+	if any.cache == nil {
+		any.IterateArray() // trigger first element read
+	}
+	return len(any.cache) != 0
 }
 
 func (any *arrayLazyAny) ToInt() int {
-	return 0
+	if any.cache == nil {
+		any.IterateArray() // trigger first element read
+	}
+	if len(any.cache) == 0 {
+		return 0
+	}
+	return 1
 }
 
 func (any *arrayLazyAny) ToInt32() int32 {
-	return 0
+	if any.cache == nil {
+		any.IterateArray() // trigger first element read
+	}
+	if len(any.cache) == 0 {
+		return 0
+	}
+	return 1
 }
 
 func (any *arrayLazyAny) ToInt64() int64 {
-	return 0
+	if any.cache == nil {
+		any.IterateArray() // trigger first element read
+	}
+	if len(any.cache) == 0 {
+		return 0
+	}
+	return 1
 }
 
 func (any *arrayLazyAny) ToFloat32() float32 {
-	return 0
+	if any.cache == nil {
+		any.IterateArray() // trigger first element read
+	}
+	if len(any.cache) == 0 {
+		return 0
+	}
+	return 1
 }
 
 func (any *arrayLazyAny) ToFloat64() float64 {
-	return 0
+	if any.cache == nil {
+		any.IterateArray() // trigger first element read
+	}
+	if len(any.cache) == 0 {
+		return 0
+	}
+	return 1
 }
 
 func (any *arrayLazyAny) ToString() string {
@@ -136,6 +175,9 @@ func (any *arrayLazyAny) Size() int {
 
 
 func (any *arrayLazyAny) IterateArray() (func() (Any, bool), bool) {
+	if any.cache == nil {
+		any.cache = make([]Any, 0, 8)
+	}
 	remaining := any.remaining
 	if len(remaining) == len(any.buf) {
 		iter := any.parse()

+ 54 - 8
feature_any_object.go

@@ -100,27 +100,60 @@ func (any *objectLazyAny) LastError() error {
 }
 
 func (any *objectLazyAny) ToBool() bool {
-	return false
+	if any.cache == nil {
+		any.IterateObject() // trigger first value read
+	}
+	return len(any.cache) != 0
 }
 
 func (any *objectLazyAny) ToInt() int {
-	return 0
+	if any.cache == nil {
+		any.IterateObject() // trigger first value read
+	}
+	if len(any.cache) == 0 {
+		return 0
+	}
+	return 1
 }
 
 func (any *objectLazyAny) ToInt32() int32 {
-	return 0
+	if any.cache == nil {
+		any.IterateObject() // trigger first value read
+	}
+	if len(any.cache) == 0 {
+		return 0
+	}
+	return 1
 }
 
 func (any *objectLazyAny) ToInt64() int64 {
-	return 0
+	if any.cache == nil {
+		any.IterateObject() // trigger first value read
+	}
+	if len(any.cache) == 0 {
+		return 0
+	}
+	return 1
 }
 
 func (any *objectLazyAny) ToFloat32() float32 {
-	return 0
+	if any.cache == nil {
+		any.IterateObject() // trigger first value read
+	}
+	if len(any.cache) == 0 {
+		return 0
+	}
+	return 1
 }
 
 func (any *objectLazyAny) ToFloat64() float64 {
-	return 0
+	if any.cache == nil {
+		any.IterateObject() // trigger first value read
+	}
+	if len(any.cache) == 0 {
+		return 0
+	}
+	return 1
 }
 
 func (any *objectLazyAny) ToString() string {
@@ -134,8 +167,16 @@ func (any *objectLazyAny) ToString() string {
 }
 
 func (any *objectLazyAny) Get(path ...interface{}) Any {
-	key := path[0].(string)
-	return any.fillCacheUntil(key)
+	if len(path) == 0 {
+		return any
+	}
+	if len(path) == 1 {
+		key := path[0].(string)
+		return any.fillCacheUntil(key)
+	} else {
+		key := path[0].(string)
+		return any.fillCacheUntil(key).Get(path[1:]...)
+	}
 }
 
 func (any *objectLazyAny) Keys() []string {
@@ -147,6 +188,11 @@ func (any *objectLazyAny) Keys() []string {
 	return keys
 }
 
+func (any *objectLazyAny) Size() int {
+	any.fillCache()
+	return len(any.cache)
+}
+
 func (any *objectLazyAny) IterateObject() (func() (string, Any, bool), bool) {
 	if any.cache == nil {
 		any.cache = map[string]Any{}

+ 2 - 0
jsoniter_array_test.go

@@ -65,6 +65,8 @@ func Test_read_two_element_array_as_any(t *testing.T) {
 	should.Nil(err)
 	should.Equal(1, any.Get(0).ToInt())
 	should.Equal(2, any.Size())
+	should.True(any.ToBool())
+	should.Equal(1, any.ToInt())
 }
 
 func Test_read_array_with_any_iterator(t *testing.T) {

+ 10 - 0
jsoniter_object_test.go

@@ -73,6 +73,9 @@ func Test_read_object_as_any(t *testing.T) {
 	any, err = UnmarshalAnyFromString(`{"a":"b","c":"d"}`)
 	// full parse
 	should.Equal(2, len(any.Keys()))
+	should.Equal(2, any.Size())
+	should.True(any.ToBool())
+	should.Equal(1, any.ToInt())
 }
 
 func Test_object_any_lazy_iterator(t *testing.T) {
@@ -137,6 +140,13 @@ func Test_object_any_with_two_lazy_iterators(t *testing.T) {
 	should.Equal("d", v.ToString())
 }
 
+func Test_object_lazy_any_get(t *testing.T) {
+	should := require.New(t)
+	any, err := UnmarshalAnyFromString(`{"a":{"b":{"c":"d"}}}`)
+	should.Nil(err)
+	should.Equal("d", any.Get("a", "b", "c").ToString())
+}
+
 func Test_write_object(t *testing.T) {
 	should := require.New(t)
 	buf := &bytes.Buffer{}