github.com/zerosnake0/jzon@v0.0.9-0.20230801092939-1b135cb83f7f/iterator_float64.go (about)

     1  package jzon
     2  
     3  import (
     4  	"io"
     5  	"strconv"
     6  )
     7  
     8  func (it *Iterator) readFloat64(c byte) (float64, error) {
     9  	if c == '-' {
    10  		c, err := it.nextByte()
    11  		if err != nil {
    12  			return 0, err
    13  		}
    14  		it.head++
    15  		f, buf, err := it.readPositiveFloat64(c, it.tmpBuffer[:0])
    16  		it.tmpBuffer = buf
    17  		return -f, err
    18  	}
    19  	f, buf, err := it.readPositiveFloat64(c, it.tmpBuffer[:0])
    20  	it.tmpBuffer = buf
    21  	return f, err
    22  }
    23  
    24  // ReadFloat64 reads a float64 value
    25  func (it *Iterator) ReadFloat64() (float64, error) {
    26  	c, err := it.nextToken()
    27  	if err != nil {
    28  		return 0, err
    29  	}
    30  	it.head++
    31  	return it.readFloat64(c)
    32  }
    33  
    34  func (it *Iterator) parseFloat64(buf []byte) (ret float64, err error) {
    35  	return strconv.ParseFloat(localByteToString(buf), 64)
    36  }
    37  
    38  func (it *Iterator) readFloat64ExponentPart(buf []byte) (ret float64, _ []byte, err error) {
    39  	c, err := it.nextByte()
    40  	if err != nil {
    41  		return 0, buf, err
    42  	}
    43  	it.head++
    44  	if c == '+' || c == '-' {
    45  		buf = append(buf, c)
    46  		c, err = it.nextByte()
    47  		if err != nil {
    48  			return 0, buf, err
    49  		}
    50  		it.head++
    51  	}
    52  	if intDigits[c] == invalidDigit {
    53  		return 0, buf, InvalidFloatError{c: c}
    54  	}
    55  	buf = append(buf, c)
    56  	for {
    57  		i := it.head
    58  		for ; i < it.tail; i++ {
    59  			c = it.buffer[i]
    60  			digit := intDigits[c]
    61  			if digit == invalidDigit {
    62  				buf = append(buf, it.buffer[it.head:i]...)
    63  				it.head = i
    64  				f, err := it.parseFloat64(buf)
    65  				return f, buf, err
    66  			}
    67  		}
    68  		// i == it.tail
    69  		buf = append(buf, it.buffer[it.head:i]...)
    70  		it.head = i
    71  		if err = it.readMore(); err != nil {
    72  			if err == io.EOF {
    73  				f, err := it.parseFloat64(buf)
    74  				return f, buf, err
    75  			}
    76  			return 0, buf, err
    77  		}
    78  	}
    79  }
    80  
    81  func (it *Iterator) readFloat64FractionPart(buf []byte) (ret float64, _ []byte, err error) {
    82  	c, err := it.nextByte()
    83  	if err != nil {
    84  		return 0, buf, err
    85  	}
    86  	if intDigits[c] == invalidDigit {
    87  		return 0, buf, InvalidFloatError{c: c}
    88  	}
    89  	it.head++
    90  	buf = append(buf, c)
    91  	for {
    92  		i := it.head
    93  		for ; i < it.tail; i++ {
    94  			c = it.buffer[i]
    95  			digit := floatDigits[c]
    96  			if digit < 0 {
    97  				switch digit {
    98  				case expInNumber:
    99  					buf = append(buf, it.buffer[it.head:i+1]...)
   100  					it.head = i + 1
   101  					return it.readFloat64ExponentPart(buf)
   102  				default:
   103  					buf = append(buf, it.buffer[it.head:i]...)
   104  					it.head = i
   105  					f, err := it.parseFloat64(buf)
   106  					return f, buf, err
   107  				}
   108  			}
   109  		}
   110  		// i == it.tail
   111  		buf = append(buf, it.buffer[it.head:i]...)
   112  		it.head = i
   113  		if err = it.readMore(); err != nil {
   114  			if err == io.EOF {
   115  				f, err := it.parseFloat64(buf)
   116  				return f, buf, err
   117  			}
   118  			return 0, buf, err
   119  		}
   120  	}
   121  }
   122  
   123  func (it *Iterator) readPositiveFloat64(c byte, buf []byte) (ret float64, _ []byte, err error) {
   124  	u := intDigits[c]
   125  	if u == invalidDigit {
   126  		return 0, buf, InvalidFloatError{c: c}
   127  	}
   128  
   129  	buf = append(buf, c)
   130  	if u == 0 {
   131  		if it.head == it.tail {
   132  			if err = it.readMore(); err != nil {
   133  				if err == io.EOF {
   134  					return 0, buf, nil
   135  				}
   136  				return 0, buf, err
   137  			}
   138  		}
   139  		switch floatDigits[it.buffer[it.head]] {
   140  		case dotInNumber:
   141  			it.head++
   142  			buf = append(buf, '.')
   143  			return it.readFloat64FractionPart(buf)
   144  		case expInNumber:
   145  			it.head++
   146  			buf = append(buf, 'e')
   147  			return it.readFloat64ExponentPart(buf)
   148  		default:
   149  			return 0, buf, nil
   150  		}
   151  	} else {
   152  		for {
   153  			i := it.head
   154  			for ; i < it.tail; i++ {
   155  				c = it.buffer[i]
   156  				digit := floatDigits[c]
   157  				if digit < 0 {
   158  					switch digit {
   159  					case dotInNumber:
   160  						buf = append(buf, it.buffer[it.head:i+1]...)
   161  						it.head = i + 1
   162  						return it.readFloat64FractionPart(buf)
   163  					case expInNumber:
   164  						buf = append(buf, it.buffer[it.head:i+1]...)
   165  						it.head = i + 1
   166  						return it.readFloat64ExponentPart(buf)
   167  					default:
   168  						buf = append(buf, it.buffer[it.head:i]...)
   169  						it.head = i
   170  						f, err := it.parseFloat64(buf)
   171  						return f, buf, err
   172  					}
   173  				}
   174  			}
   175  			// i == it.tail
   176  			buf = append(buf, it.buffer[it.head:i]...)
   177  			it.head = i
   178  			if err = it.readMore(); err != nil {
   179  				if err == io.EOF {
   180  					f, err := it.parseFloat64(buf)
   181  					return f, buf, err
   182  				}
   183  				return 0, buf, err
   184  			}
   185  		}
   186  	}
   187  }