summaryrefslogtreecommitdiff
path: root/src/math
diff options
context:
space:
mode:
authorJT Olio <hello@jtolio.com>2019-05-06 17:38:23 -0600
committerRobert Griesemer <gri@golang.org>2019-05-08 17:11:57 +0000
commit5a2da5624a9403a61cdd8df529e2b71129ef7898 (patch)
treeaaa0a952403700a5fe2fb74e62751780369e2046 /src/math
parent7f5434c44c75f25172d5d6106ad179d2e813bdd1 (diff)
downloadgo-git-5a2da5624a9403a61cdd8df529e2b71129ef7898.tar.gz
math/big: stack allocate scaleDenom return value
benchmark old ns/op new ns/op delta BenchmarkRatCmp-4 154 77.9 -49.42% Change-Id: I932710ad8b6905879e232168b1777927f86ba22a Reviewed-on: https://go-review.googlesource.com/c/go/+/175460 Run-TryBot: Robert Griesemer <gri@golang.org> Reviewed-by: Robert Griesemer <gri@golang.org>
Diffstat (limited to 'src/math')
-rw-r--r--src/math/big/rat.go35
-rw-r--r--src/math/big/rat_test.go7
2 files changed, 27 insertions, 15 deletions
diff --git a/src/math/big/rat.go b/src/math/big/rat.go
index 675889f33b..c8bf698b18 100644
--- a/src/math/big/rat.go
+++ b/src/math/big/rat.go
@@ -462,16 +462,15 @@ func mulDenom(z, x, y nat) nat {
return z.mul(x, y)
}
-// scaleDenom computes x*f.
-// If f == 0 (zero value of denominator), the result is (a copy of) x.
-func scaleDenom(x *Int, f nat) *Int {
- var z Int
+// scaleDenom sets z to the product x*f.
+// If f == 0 (zero value of denominator), z is set to (a copy of) x.
+func (z *Int) scaleDenom(x *Int, f nat) {
if len(f) == 0 {
- return z.Set(x)
+ z.Set(x)
+ return
}
z.abs = z.abs.mul(x.abs, f)
z.neg = x.neg
- return &z
}
// Cmp compares x and y and returns:
@@ -481,23 +480,28 @@ func scaleDenom(x *Int, f nat) *Int {
// +1 if x > y
//
func (x *Rat) Cmp(y *Rat) int {
- return scaleDenom(&x.a, y.b.abs).Cmp(scaleDenom(&y.a, x.b.abs))
+ var a, b Int
+ a.scaleDenom(&x.a, y.b.abs)
+ b.scaleDenom(&y.a, x.b.abs)
+ return a.Cmp(&b)
}
// Add sets z to the sum x+y and returns z.
func (z *Rat) Add(x, y *Rat) *Rat {
- a1 := scaleDenom(&x.a, y.b.abs)
- a2 := scaleDenom(&y.a, x.b.abs)
- z.a.Add(a1, a2)
+ var a1, a2 Int
+ a1.scaleDenom(&x.a, y.b.abs)
+ a2.scaleDenom(&y.a, x.b.abs)
+ z.a.Add(&a1, &a2)
z.b.abs = mulDenom(z.b.abs, x.b.abs, y.b.abs)
return z.norm()
}
// Sub sets z to the difference x-y and returns z.
func (z *Rat) Sub(x, y *Rat) *Rat {
- a1 := scaleDenom(&x.a, y.b.abs)
- a2 := scaleDenom(&y.a, x.b.abs)
- z.a.Sub(a1, a2)
+ var a1, a2 Int
+ a1.scaleDenom(&x.a, y.b.abs)
+ a2.scaleDenom(&y.a, x.b.abs)
+ z.a.Sub(&a1, &a2)
z.b.abs = mulDenom(z.b.abs, x.b.abs, y.b.abs)
return z.norm()
}
@@ -522,8 +526,9 @@ func (z *Rat) Quo(x, y *Rat) *Rat {
if len(y.a.abs) == 0 {
panic("division by zero")
}
- a := scaleDenom(&x.a, y.b.abs)
- b := scaleDenom(&y.a, x.b.abs)
+ var a, b Int
+ a.scaleDenom(&x.a, y.b.abs)
+ b.scaleDenom(&y.a, x.b.abs)
z.a.abs = a.abs
z.b.abs = b.abs
z.a.neg = a.neg != b.neg
diff --git a/src/math/big/rat_test.go b/src/math/big/rat_test.go
index b169477e23..83c5d5cfea 100644
--- a/src/math/big/rat_test.go
+++ b/src/math/big/rat_test.go
@@ -671,3 +671,10 @@ func TestRatSetUint64(t *testing.T) {
}
}
}
+
+func BenchmarkRatCmp(b *testing.B) {
+ x, y := NewRat(4, 1), NewRat(7, 2)
+ for i := 0; i < b.N; i++ {
+ x.Cmp(y)
+ }
+}