number of bits
(e *encodeState, v reflect.Value, opts encOpts)
| 545 | type floatEncoder int // number of bits |
| 546 | |
| 547 | func (bits floatEncoder) encode(e *encodeState, v reflect.Value, opts encOpts) { |
| 548 | f := v.Float() |
| 549 | if math.IsInf(f, 0) || math.IsNaN(f) { |
| 550 | e.error(&UnsupportedValueError{v, strconv.FormatFloat(f, 'g', -1, int(bits))}) |
| 551 | } |
| 552 | |
| 553 | // Convert as if by ES6 number to string conversion. |
| 554 | // This matches most other JSON generators. |
| 555 | // See golang.org/issue/6384 and golang.org/issue/14135. |
| 556 | // Like fmt %g, but the exponent cutoffs are different |
| 557 | // and exponents themselves are not padded to two digits. |
| 558 | b := e.scratch[:0] |
| 559 | abs := math.Abs(f) |
| 560 | fmt := byte('f') |
| 561 | // Note: Must use float32 comparisons for underlying float32 value to get precise cutoffs right. |
| 562 | if abs != 0 { |
| 563 | if bits == 64 && (abs < 1e-6 || abs >= 1e21) || bits == 32 && (float32(abs) < 1e-6 || float32(abs) >= 1e21) { |
| 564 | fmt = 'e' |
| 565 | } |
| 566 | } |
| 567 | b = strconv.AppendFloat(b, f, fmt, -1, int(bits)) |
| 568 | if fmt == 'e' { |
| 569 | // clean up e-09 to e-9 |
| 570 | n := len(b) |
| 571 | if n >= 4 && b[n-4] == 'e' && b[n-3] == '-' && b[n-2] == '0' { |
| 572 | b[n-2] = b[n-1] |
| 573 | b = b[:n-1] |
| 574 | } |
| 575 | } |
| 576 | |
| 577 | if opts.quoted { |
| 578 | e.WriteByte('"') |
| 579 | } |
| 580 | e.Write(b) |
| 581 | if opts.quoted { |
| 582 | e.WriteByte('"') |
| 583 | } |
| 584 | } |
| 585 | |
| 586 | var ( |
| 587 | float32Encoder = (floatEncoder(32)).encode |