feature_reflect_array.go 4.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158
  1. package jsoniter
  2. import (
  3. "fmt"
  4. "io"
  5. "reflect"
  6. "unsafe"
  7. )
  8. func decoderOfSlice(typ reflect.Type) (Decoder, error) {
  9. decoder, err := decoderOfType(typ.Elem())
  10. if err != nil {
  11. return nil, err
  12. }
  13. return &sliceDecoder{typ, typ.Elem(), decoder}, nil
  14. }
  15. func encoderOfSlice(typ reflect.Type) (Encoder, error) {
  16. encoder, err := encoderOfType(typ.Elem())
  17. if err != nil {
  18. return nil, err
  19. }
  20. if typ.Elem().Kind() == reflect.Map {
  21. encoder = &optionalEncoder{encoder}
  22. }
  23. return &sliceEncoder{typ, typ.Elem(), encoder}, nil
  24. }
  25. type sliceEncoder struct {
  26. sliceType reflect.Type
  27. elemType reflect.Type
  28. elemEncoder Encoder
  29. }
  30. func (encoder *sliceEncoder) encode(ptr unsafe.Pointer, stream *Stream) {
  31. slice := (*sliceHeader)(ptr)
  32. if slice.Len == 0 {
  33. stream.WriteEmptyArray()
  34. return
  35. }
  36. stream.WriteArrayStart()
  37. elemPtr := uintptr(slice.Data)
  38. encoder.elemEncoder.encode(unsafe.Pointer(elemPtr), stream)
  39. for i := 1; i < slice.Len; i++ {
  40. stream.WriteMore()
  41. elemPtr += encoder.elemType.Size()
  42. encoder.elemEncoder.encode(unsafe.Pointer(elemPtr), stream)
  43. }
  44. stream.WriteArrayEnd()
  45. if stream.Error != nil && stream.Error != io.EOF {
  46. stream.Error = fmt.Errorf("%v: %s", encoder.sliceType, stream.Error.Error())
  47. }
  48. }
  49. func (encoder *sliceEncoder) encodeInterface(val interface{}, stream *Stream) {
  50. writeToStream(val, stream, encoder)
  51. }
  52. func (encoder *sliceEncoder) isEmpty(ptr unsafe.Pointer) bool {
  53. slice := (*sliceHeader)(ptr)
  54. return slice.Len == 0
  55. }
  56. type sliceDecoder struct {
  57. sliceType reflect.Type
  58. elemType reflect.Type
  59. elemDecoder Decoder
  60. }
  61. // sliceHeader is a safe version of SliceHeader used within this package.
  62. type sliceHeader struct {
  63. Data unsafe.Pointer
  64. Len int
  65. Cap int
  66. }
  67. func (decoder *sliceDecoder) decode(ptr unsafe.Pointer, iter *Iterator) {
  68. decoder.doDecode(ptr, iter)
  69. if iter.Error != nil && iter.Error != io.EOF {
  70. iter.Error = fmt.Errorf("%v: %s", decoder.sliceType, iter.Error.Error())
  71. }
  72. }
  73. func (decoder *sliceDecoder) doDecode(ptr unsafe.Pointer, iter *Iterator) {
  74. slice := (*sliceHeader)(ptr)
  75. reuseSlice(slice, decoder.sliceType, 4)
  76. if !iter.ReadArray() {
  77. return
  78. }
  79. offset := uintptr(0)
  80. decoder.elemDecoder.decode(unsafe.Pointer(uintptr(slice.Data)+offset), iter)
  81. if !iter.ReadArray() {
  82. slice.Len = 1
  83. return
  84. }
  85. offset += decoder.elemType.Size()
  86. decoder.elemDecoder.decode(unsafe.Pointer(uintptr(slice.Data)+offset), iter)
  87. if !iter.ReadArray() {
  88. slice.Len = 2
  89. return
  90. }
  91. offset += decoder.elemType.Size()
  92. decoder.elemDecoder.decode(unsafe.Pointer(uintptr(slice.Data)+offset), iter)
  93. if !iter.ReadArray() {
  94. slice.Len = 3
  95. return
  96. }
  97. offset += decoder.elemType.Size()
  98. decoder.elemDecoder.decode(unsafe.Pointer(uintptr(slice.Data)+offset), iter)
  99. slice.Len = 4
  100. for iter.ReadArray() {
  101. growOne(slice, decoder.sliceType, decoder.elemType)
  102. offset += decoder.elemType.Size()
  103. decoder.elemDecoder.decode(unsafe.Pointer(uintptr(slice.Data)+offset), iter)
  104. }
  105. }
  106. // grow grows the slice s so that it can hold extra more values, allocating
  107. // more capacity if needed. It also returns the old and new slice lengths.
  108. func growOne(slice *sliceHeader, sliceType reflect.Type, elementType reflect.Type) {
  109. newLen := slice.Len + 1
  110. if newLen <= slice.Cap {
  111. slice.Len = newLen
  112. return
  113. }
  114. newCap := slice.Cap
  115. if newCap == 0 {
  116. newCap = 1
  117. } else {
  118. for newCap < newLen {
  119. if slice.Len < 1024 {
  120. newCap += newCap
  121. } else {
  122. newCap += newCap / 4
  123. }
  124. }
  125. }
  126. dst := unsafe.Pointer(reflect.MakeSlice(sliceType, newLen, newCap).Pointer())
  127. // copy old array into new array
  128. originalBytesCount := uintptr(slice.Len) * elementType.Size()
  129. srcPtr := (*[1 << 30]byte)(slice.Data)
  130. dstPtr := (*[1 << 30]byte)(dst)
  131. for i := uintptr(0); i < originalBytesCount; i++ {
  132. dstPtr[i] = srcPtr[i]
  133. }
  134. slice.Len = newLen
  135. slice.Cap = newCap
  136. slice.Data = dst
  137. }
  138. func reuseSlice(slice *sliceHeader, sliceType reflect.Type, expectedCap int) {
  139. if expectedCap <= slice.Cap {
  140. return
  141. }
  142. dst := unsafe.Pointer(reflect.MakeSlice(sliceType, 0, expectedCap).Pointer())
  143. slice.Cap = expectedCap
  144. slice.Data = dst
  145. }