feature_reflect_array.go 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110
  1. package jsoniter
  2. import (
  3. "fmt"
  4. "io"
  5. "reflect"
  6. "unsafe"
  7. )
  8. func decoderOfArray(cfg *frozenConfig, prefix string, typ reflect.Type) ValDecoder {
  9. decoder := decoderOfType(cfg, prefix+"[array]->", typ.Elem())
  10. return &arrayDecoder{typ, typ.Elem(), decoder}
  11. }
  12. func encoderOfArray(cfg *frozenConfig, prefix string, typ reflect.Type) ValEncoder {
  13. if typ.Len() == 0 {
  14. return emptyArrayEncoder{}
  15. }
  16. encoder := encoderOfType(cfg, prefix+"[array]->", typ.Elem())
  17. if typ.Elem().Kind() == reflect.Map {
  18. encoder = &OptionalEncoder{encoder}
  19. }
  20. return &arrayEncoder{typ, typ.Elem(), encoder}
  21. }
  22. type emptyArrayEncoder struct{}
  23. func (encoder emptyArrayEncoder) Encode(ptr unsafe.Pointer, stream *Stream) {
  24. stream.WriteEmptyArray()
  25. }
  26. func (encoder emptyArrayEncoder) EncodeInterface(val interface{}, stream *Stream) {
  27. stream.WriteEmptyArray()
  28. }
  29. func (encoder emptyArrayEncoder) IsEmpty(ptr unsafe.Pointer) bool {
  30. return true
  31. }
  32. type arrayEncoder struct {
  33. arrayType reflect.Type
  34. elemType reflect.Type
  35. elemEncoder ValEncoder
  36. }
  37. func (encoder *arrayEncoder) Encode(ptr unsafe.Pointer, stream *Stream) {
  38. stream.WriteArrayStart()
  39. elemPtr := unsafe.Pointer(ptr)
  40. encoder.elemEncoder.Encode(elemPtr, stream)
  41. for i := 1; i < encoder.arrayType.Len(); i++ {
  42. stream.WriteMore()
  43. elemPtr = unsafe.Pointer(uintptr(elemPtr) + encoder.elemType.Size())
  44. encoder.elemEncoder.Encode(unsafe.Pointer(elemPtr), stream)
  45. }
  46. stream.WriteArrayEnd()
  47. if stream.Error != nil && stream.Error != io.EOF {
  48. stream.Error = fmt.Errorf("%v: %s", encoder.arrayType, stream.Error.Error())
  49. }
  50. }
  51. func (encoder *arrayEncoder) EncodeInterface(val interface{}, stream *Stream) {
  52. // special optimization for interface{}
  53. e := (*emptyInterface)(unsafe.Pointer(&val))
  54. if e.word == nil {
  55. stream.WriteArrayStart()
  56. stream.WriteNil()
  57. stream.WriteArrayEnd()
  58. return
  59. }
  60. elemType := encoder.arrayType.Elem()
  61. if encoder.arrayType.Len() == 1 && (elemType.Kind() == reflect.Ptr || elemType.Kind() == reflect.Map) {
  62. ptr := uintptr(e.word)
  63. e.word = unsafe.Pointer(&ptr)
  64. }
  65. if reflect.TypeOf(val).Kind() == reflect.Ptr {
  66. encoder.Encode(unsafe.Pointer(&e.word), stream)
  67. } else {
  68. encoder.Encode(e.word, stream)
  69. }
  70. }
  71. func (encoder *arrayEncoder) IsEmpty(ptr unsafe.Pointer) bool {
  72. return false
  73. }
  74. type arrayDecoder struct {
  75. arrayType reflect.Type
  76. elemType reflect.Type
  77. elemDecoder ValDecoder
  78. }
  79. func (decoder *arrayDecoder) Decode(ptr unsafe.Pointer, iter *Iterator) {
  80. decoder.doDecode(ptr, iter)
  81. if iter.Error != nil && iter.Error != io.EOF {
  82. iter.Error = fmt.Errorf("%v: %s", decoder.arrayType, iter.Error.Error())
  83. }
  84. }
  85. func (decoder *arrayDecoder) doDecode(ptr unsafe.Pointer, iter *Iterator) {
  86. offset := uintptr(0)
  87. iter.ReadArrayCB(func(iter *Iterator) bool {
  88. if offset < decoder.arrayType.Size() {
  89. decoder.elemDecoder.Decode(unsafe.Pointer(uintptr(ptr)+offset), iter)
  90. offset += decoder.elemType.Size()
  91. } else {
  92. iter.Skip()
  93. }
  94. return true
  95. })
  96. }