Commit db96e682 authored by Robert Griesemer's avatar Robert Griesemer

math/big: clearer semantics for Float.Scan

Change-Id: I72e8389ec080be8a0119f98df898de6f5510fa4d
Reviewed-on: https://go-review.googlesource.com/7693Reviewed-by: default avatarAlan Donovan <adonovan@google.com>
parent bc149897
...@@ -63,12 +63,21 @@ func (z *Float) SetString(s string) (*Float, bool) { ...@@ -63,12 +63,21 @@ func (z *Float) SetString(s string) (*Float, bool) {
// be binary, if present (an "e" or "E" exponent indicator cannot be // be binary, if present (an "e" or "E" exponent indicator cannot be
// distinguished from a mantissa digit). // distinguished from a mantissa digit).
// //
// The returned *Float f is nil and the value of z is valid but not
// defined if an error is reported.
//
// BUG(gri) The Float.Scan signature conflicts with Scan(s fmt.ScanState, ch rune) error. // BUG(gri) The Float.Scan signature conflicts with Scan(s fmt.ScanState, ch rune) error.
func (z *Float) Scan(r io.ByteScanner, base int) (f *Float, b int, err error) { func (z *Float) Scan(r io.ByteScanner, base int) (f *Float, b int, err error) {
if z.prec == 0 { prec := z.prec
z.prec = 64 if prec == 0 {
prec = 64
} }
// NaNs ignore sign, mantissa, and exponent so we can set
// them below while having a valid value for z in case of
// errors.
z.SetNaN()
// sign // sign
z.neg, err = scanSign(r) z.neg, err = scanSign(r)
if err != nil { if err != nil {
...@@ -90,13 +99,12 @@ func (z *Float) Scan(r io.ByteScanner, base int) (f *Float, b int, err error) { ...@@ -90,13 +99,12 @@ func (z *Float) Scan(r io.ByteScanner, base int) (f *Float, b int, err error) {
return return
} }
// set result
f = z
// special-case 0 // special-case 0
if len(z.mant) == 0 { if len(z.mant) == 0 {
z.prec = prec
z.acc = Exact z.acc = Exact
z.form = zero z.form = zero
f = z
return return
} }
// len(z.mant) > 0 // len(z.mant) > 0
...@@ -141,10 +149,11 @@ func (z *Float) Scan(r io.ByteScanner, base int) (f *Float, b int, err error) { ...@@ -141,10 +149,11 @@ func (z *Float) Scan(r io.ByteScanner, base int) (f *Float, b int, err error) {
// apply 2**exp2 // apply 2**exp2
if MinExp <= exp2 && exp2 <= MaxExp { if MinExp <= exp2 && exp2 <= MaxExp {
z.prec = prec
z.form = finite z.form = finite
z.exp = int32(exp2) z.exp = int32(exp2)
f = z
} else { } else {
f = nil
err = fmt.Errorf("exponent overflow") err = fmt.Errorf("exponent overflow")
return return
} }
...@@ -175,8 +184,8 @@ func (z *Float) Scan(r io.ByteScanner, base int) (f *Float, b int, err error) { ...@@ -175,8 +184,8 @@ func (z *Float) Scan(r io.ByteScanner, base int) (f *Float, b int, err error) {
} }
// Parse is like z.Scan(r, base), but instead of reading from an // Parse is like z.Scan(r, base), but instead of reading from an
// io.ByteScanner, it parses the string s. An error is returned if // io.ByteScanner, it parses the string s. An error is also returned
// the string contains invalid or trailing bytes not belonging to // if the string contains invalid or trailing bytes not belonging to
// the number. // the number.
func (z *Float) Parse(s string, base int) (f *Float, b int, err error) { func (z *Float) Parse(s string, base int) (f *Float, b int, err error) {
r := strings.NewReader(s) r := strings.NewReader(s)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment