jsoniter_float_test.go 6.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217
  1. // +build go1.8
  2. package jsoniter
  3. import (
  4. "bytes"
  5. "encoding/json"
  6. "fmt"
  7. "strconv"
  8. "testing"
  9. "github.com/stretchr/testify/require"
  10. )
  11. func Test_read_big_float(t *testing.T) {
  12. should := require.New(t)
  13. iter := ParseString(ConfigDefault, `12.3`)
  14. val := iter.ReadBigFloat()
  15. val64, _ := val.Float64()
  16. should.Equal(12.3, val64)
  17. }
  18. func Test_read_big_int(t *testing.T) {
  19. should := require.New(t)
  20. iter := ParseString(ConfigDefault, `92233720368547758079223372036854775807`)
  21. val := iter.ReadBigInt()
  22. should.NotNil(val)
  23. should.Equal(`92233720368547758079223372036854775807`, val.String())
  24. }
  25. func Test_read_float(t *testing.T) {
  26. inputs := []string{
  27. `1.1`, `1000`, `9223372036854775807`, `12.3`, `-12.3`, `720368.54775807`, `720368.547758075`,
  28. `1e1`, `1e+1`, `1e-1`, `1E1`, `1E+1`, `1E-1`, `-1e1`, `-1e+1`, `-1e-1`,
  29. }
  30. for _, input := range inputs {
  31. // non-streaming
  32. t.Run(fmt.Sprintf("%v", input), func(t *testing.T) {
  33. should := require.New(t)
  34. iter := ParseString(ConfigDefault, input+",")
  35. expected, err := strconv.ParseFloat(input, 32)
  36. should.Nil(err)
  37. should.Equal(float32(expected), iter.ReadFloat32())
  38. })
  39. t.Run(fmt.Sprintf("%v", input), func(t *testing.T) {
  40. should := require.New(t)
  41. iter := ParseString(ConfigDefault, input+",")
  42. expected, err := strconv.ParseFloat(input, 64)
  43. should.Nil(err)
  44. should.Equal(expected, iter.ReadFloat64())
  45. })
  46. // streaming
  47. t.Run(fmt.Sprintf("%v", input), func(t *testing.T) {
  48. should := require.New(t)
  49. iter := Parse(ConfigDefault, bytes.NewBufferString(input+","), 2)
  50. expected, err := strconv.ParseFloat(input, 32)
  51. should.Nil(err)
  52. should.Equal(float32(expected), iter.ReadFloat32())
  53. })
  54. t.Run(fmt.Sprintf("%v", input), func(t *testing.T) {
  55. should := require.New(t)
  56. iter := Parse(ConfigDefault, bytes.NewBufferString(input+","), 2)
  57. val := float64(0)
  58. err := json.Unmarshal([]byte(input), &val)
  59. should.Nil(err)
  60. should.Equal(val, iter.ReadFloat64())
  61. })
  62. }
  63. }
  64. func Test_read_float_as_interface(t *testing.T) {
  65. should := require.New(t)
  66. iter := ParseString(ConfigDefault, `12.3`)
  67. should.Equal(float64(12.3), iter.Read())
  68. }
  69. func Test_wrap_float(t *testing.T) {
  70. should := require.New(t)
  71. str, err := MarshalToString(WrapFloat64(12.3))
  72. should.Nil(err)
  73. should.Equal("12.3", str)
  74. }
  75. func Test_write_float32(t *testing.T) {
  76. vals := []float32{0, 1, -1, 99, 0xff, 0xfff, 0xffff, 0xfffff, 0xffffff, 0x4ffffff, 0xfffffff,
  77. -0x4ffffff, -0xfffffff, 1.2345, 1.23456, 1.234567, 1.001}
  78. for _, val := range vals {
  79. t.Run(fmt.Sprintf("%v", val), func(t *testing.T) {
  80. should := require.New(t)
  81. buf := &bytes.Buffer{}
  82. stream := NewStream(ConfigDefault, buf, 4096)
  83. stream.WriteFloat32Lossy(val)
  84. stream.Flush()
  85. should.Nil(stream.Error)
  86. output, err := json.Marshal(val)
  87. should.Nil(err)
  88. should.Equal(string(output), buf.String())
  89. })
  90. t.Run(fmt.Sprintf("%v", val), func(t *testing.T) {
  91. should := require.New(t)
  92. buf := &bytes.Buffer{}
  93. stream := NewStream(ConfigDefault, buf, 4096)
  94. stream.WriteVal(val)
  95. stream.Flush()
  96. should.Nil(stream.Error)
  97. output, err := json.Marshal(val)
  98. should.Nil(err)
  99. should.Equal(string(output), buf.String())
  100. })
  101. }
  102. should := require.New(t)
  103. buf := &bytes.Buffer{}
  104. stream := NewStream(ConfigDefault, buf, 10)
  105. stream.WriteRaw("abcdefg")
  106. stream.WriteFloat32Lossy(1.123456)
  107. stream.Flush()
  108. should.Nil(stream.Error)
  109. should.Equal("abcdefg1.123456", buf.String())
  110. stream = NewStream(ConfigDefault, nil, 0)
  111. stream.WriteFloat32(float32(0.0000001))
  112. should.Equal("1e-07", string(stream.buf))
  113. }
  114. func Test_write_float64(t *testing.T) {
  115. vals := []float64{0, 1, -1, 99, 0xff, 0xfff, 0xffff, 0xfffff, 0xffffff, 0x4ffffff, 0xfffffff,
  116. -0x4ffffff, -0xfffffff, 1.2345, 1.23456, 1.234567, 1.001}
  117. for _, val := range vals {
  118. t.Run(fmt.Sprintf("%v", val), func(t *testing.T) {
  119. should := require.New(t)
  120. buf := &bytes.Buffer{}
  121. stream := NewStream(ConfigDefault, buf, 4096)
  122. stream.WriteFloat64Lossy(val)
  123. stream.Flush()
  124. should.Nil(stream.Error)
  125. should.Equal(strconv.FormatFloat(val, 'f', -1, 64), buf.String())
  126. })
  127. t.Run(fmt.Sprintf("%v", val), func(t *testing.T) {
  128. should := require.New(t)
  129. buf := &bytes.Buffer{}
  130. stream := NewStream(ConfigDefault, buf, 4096)
  131. stream.WriteVal(val)
  132. stream.Flush()
  133. should.Nil(stream.Error)
  134. should.Equal(strconv.FormatFloat(val, 'f', -1, 64), buf.String())
  135. })
  136. }
  137. should := require.New(t)
  138. buf := &bytes.Buffer{}
  139. stream := NewStream(ConfigDefault, buf, 10)
  140. stream.WriteRaw("abcdefg")
  141. stream.WriteFloat64Lossy(1.123456)
  142. stream.Flush()
  143. should.Nil(stream.Error)
  144. should.Equal("abcdefg1.123456", buf.String())
  145. stream = NewStream(ConfigDefault, nil, 0)
  146. stream.WriteFloat64(float64(0.0000001))
  147. should.Equal("1e-07", string(stream.buf))
  148. }
  149. func Test_read_float64_cursor(t *testing.T) {
  150. should := require.New(t)
  151. iter := ParseString(ConfigDefault, "[1.23456789\n,2,3]")
  152. should.True(iter.ReadArray())
  153. should.Equal(1.23456789, iter.Read())
  154. should.True(iter.ReadArray())
  155. should.Equal(float64(2), iter.Read())
  156. }
  157. func Test_read_float_scientific(t *testing.T) {
  158. should := require.New(t)
  159. var obj interface{}
  160. should.Nil(UnmarshalFromString(`1e1`, &obj))
  161. should.Equal(float64(10), obj)
  162. should.Nil(json.Unmarshal([]byte(`1e1`), &obj))
  163. should.Equal(float64(10), obj)
  164. should.Nil(UnmarshalFromString(`1.0e1`, &obj))
  165. should.Equal(float64(10), obj)
  166. should.Nil(json.Unmarshal([]byte(`1.0e1`), &obj))
  167. should.Equal(float64(10), obj)
  168. }
  169. func Test_lossy_float_marshal(t *testing.T) {
  170. should := require.New(t)
  171. api := Config{MarshalFloatWith6Digits: true}.Froze()
  172. output, err := api.MarshalToString(float64(0.1234567))
  173. should.Nil(err)
  174. should.Equal("0.123457", output)
  175. output, err = api.MarshalToString(float32(0.1234567))
  176. should.Nil(err)
  177. should.Equal("0.123457", output)
  178. }
  179. func Test_read_number(t *testing.T) {
  180. should := require.New(t)
  181. iter := ParseString(ConfigDefault, `92233720368547758079223372036854775807`)
  182. val := iter.ReadNumber()
  183. should.Equal(`92233720368547758079223372036854775807`, string(val))
  184. }
  185. func Benchmark_jsoniter_float(b *testing.B) {
  186. b.ReportAllocs()
  187. input := []byte(`1.1123,`)
  188. iter := NewIterator(ConfigDefault)
  189. for n := 0; n < b.N; n++ {
  190. iter.ResetBytes(input)
  191. iter.ReadFloat64()
  192. }
  193. }
  194. func Benchmark_json_float(b *testing.B) {
  195. for n := 0; n < b.N; n++ {
  196. result := float64(0)
  197. json.Unmarshal([]byte(`1.1`), &result)
  198. }
  199. }