aboutsummaryrefslogtreecommitdiff
path: root/src/math/big/floatmarsh_test.go
diff options
context:
space:
mode:
authorRobert Griesemer <gri@golang.org>2016-04-20 13:40:55 -0700
committerRobert Griesemer <gri@golang.org>2016-04-20 21:16:21 +0000
commitaea224386ea7c10c07490bb6cdef12a51fa9a9cf (patch)
tree659b34a9a6dd85fee53d5962f8956ceca571309c /src/math/big/floatmarsh_test.go
parent60fd32a47fdffb95d3646c9fc75acc9beff67183 (diff)
downloadgo-aea224386ea7c10c07490bb6cdef12a51fa9a9cf.tar.xz
math/big: more tests, documentation for Flot gob marshalling
Follow-up to https://golang.org/cl/21755. This turned out to be a bit more than just a few nits as originally expected in that CL. 1) The actual mantissa may be shorter than required for the given precision (because of trailing 0's): no need to allocate space for it (and transmit 0's). This can save a lot of space when the precision is high: E.g., for prec == 1000, 16 words or 128 bytes are required at the most, but if the actual number is short, it may be much less (for the test cases present, it's significantly less). 2) The actual mantissa may be longer than the number of words required for the given precision: make sure to not overflow when encoding in bytes. 3) Add more documentation. 4) Add more tests. Change-Id: I9f40c408cfdd9183a8e81076d2f7d6c75e7a00e9 Reviewed-on: https://go-review.googlesource.com/22324 Reviewed-by: Alan Donovan <adonovan@google.com>
Diffstat (limited to 'src/math/big/floatmarsh_test.go')
-rw-r--r--src/math/big/floatmarsh_test.go81
1 files changed, 50 insertions, 31 deletions
diff --git a/src/math/big/floatmarsh_test.go b/src/math/big/floatmarsh_test.go
index f726c35e99..5bd906ddae 100644
--- a/src/math/big/floatmarsh_test.go
+++ b/src/math/big/floatmarsh_test.go
@@ -28,43 +28,60 @@ var floatVals = []string{
func TestFloatGobEncoding(t *testing.T) {
var medium bytes.Buffer
+ enc := gob.NewEncoder(&medium)
+ dec := gob.NewDecoder(&medium)
for _, test := range floatVals {
for _, sign := range []string{"", "+", "-"} {
for _, prec := range []uint{0, 1, 2, 10, 53, 64, 100, 1000} {
- medium.Reset() // empty buffer for each test case (in case of failures)
- enc := gob.NewEncoder(&medium)
- dec := gob.NewDecoder(&medium)
- x := sign + test
- var tx Float
- _, _, err := tx.SetPrec(prec).Parse(x, 0)
- if err != nil {
- t.Errorf("parsing of %s (prec = %d) failed (invalid test case): %v", x, prec, err)
- continue
- }
- tx.SetMode(ToPositiveInf)
- if err := enc.Encode(&tx); err != nil {
- t.Errorf("encoding of %v (prec = %d) failed: %v", &tx, prec, err)
- continue
- }
+ for _, mode := range []RoundingMode{ToNearestEven, ToNearestAway, ToZero, AwayFromZero, ToNegativeInf, ToPositiveInf} {
+ medium.Reset() // empty buffer for each test case (in case of failures)
+ x := sign + test
- var rx Float
- if err := dec.Decode(&rx); err != nil {
- t.Errorf("decoding of %v (prec = %d) failed: %v", &tx, prec, err)
- continue
- }
+ var tx Float
+ _, _, err := tx.SetPrec(prec).SetMode(mode).Parse(x, 0)
+ if err != nil {
+ t.Errorf("parsing of %s (%dbits, %v) failed (invalid test case): %v", x, prec, mode, err)
+ continue
+ }
- if rx.Cmp(&tx) != 0 {
- t.Errorf("transmission of %s failed: got %s want %s", x, rx.String(), tx.String())
- continue
- }
+ // If tx was set to prec == 0, tx.Parse(x, 0) assumes precision 64. Correct it.
+ if prec == 0 {
+ tx.SetPrec(0)
+ }
+
+ if err := enc.Encode(&tx); err != nil {
+ t.Errorf("encoding of %v (%dbits, %v) failed: %v", &tx, prec, mode, err)
+ continue
+ }
+
+ var rx Float
+ if err := dec.Decode(&rx); err != nil {
+ t.Errorf("decoding of %v (%dbits, %v) failed: %v", &tx, prec, mode, err)
+ continue
+ }
+
+ if rx.Cmp(&tx) != 0 {
+ t.Errorf("transmission of %s failed: got %s want %s", x, rx.String(), tx.String())
+ continue
+ }
+
+ if rx.Prec() != prec {
+ t.Errorf("transmission of %s's prec failed: got %d want %d", x, rx.Prec(), prec)
+ }
+
+ if rx.Mode() != mode {
+ t.Errorf("transmission of %s's mode failed: got %s want %s", x, rx.Mode(), mode)
+ }
- if rx.Mode() != ToPositiveInf {
- t.Errorf("transmission of %s's mode failed: got %s want %s", x, rx.Mode(), ToPositiveInf)
+ if rx.Acc() != tx.Acc() {
+ t.Errorf("transmission of %s's accuracy failed: got %s want %s", x, rx.Acc(), tx.Acc())
+ }
}
}
}
}
}
+
func TestFloatCorruptGob(t *testing.T) {
var buf bytes.Buffer
tx := NewFloat(4 / 3).SetPrec(1000).SetMode(ToPositiveInf)
@@ -72,20 +89,22 @@ func TestFloatCorruptGob(t *testing.T) {
t.Fatal(err)
}
b := buf.Bytes()
+
var rx Float
if err := gob.NewDecoder(bytes.NewReader(b)).Decode(&rx); err != nil {
t.Fatal(err)
}
- var rx2 Float
- if err := gob.NewDecoder(bytes.NewReader(b[:10])).Decode(&rx2); err != io.ErrUnexpectedEOF {
- t.Errorf("expected io.ErrUnexpectedEOF, got %v", err)
+
+ if err := gob.NewDecoder(bytes.NewReader(b[:10])).Decode(&rx); err != io.ErrUnexpectedEOF {
+ t.Errorf("got %v want EOF", err)
}
+
b[1] = 0
if err := gob.NewDecoder(bytes.NewReader(b)).Decode(&rx); err == nil {
- t.Fatal("expected a version error, got nil")
+ t.Fatal("got nil want version error")
}
-
}
+
func TestFloatJSONEncoding(t *testing.T) {
for _, test := range floatVals {
for _, sign := range []string{"", "+", "-"} {