Skip to content

Commit d7f28eb

Browse files
Speedup log2 code (#7106) (#7110)
* Speedup log2 code * Update changelog (cherry picked from commit fc3ccf2) Co-authored-by: Dev Ojha <ValarDragon@users.noreply.github.com>
1 parent f7c9600 commit d7f28eb

File tree

2 files changed

+15
-8
lines changed

2 files changed

+15
-8
lines changed

CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
4545
### Misc Improvements
4646

4747
* [#7093](https://github.com/osmosis-labs/osmosis/pull/7093),[#7100](https://github.com/osmosis-labs/osmosis/pull/7100) Lower CPU overheads of the Osmosis epoch.
48+
* [#7106](https://github.com/osmosis-labs/osmosis/pull/7106) Halve the time of log2 calculation (speeds up TWAP code)
49+
4850

4951
## v20.5.1
5052

osmomath/decimal.go

Lines changed: 13 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,11 @@ var (
5858

5959
// precisionFactors are used to adjust the scale of big.Int values to match the desired precision
6060
precisionFactors = make(map[uint64]*big.Int)
61+
62+
zeroBigDec BigDec = ZeroBigDec()
63+
oneBigDec BigDec = OneBigDec()
64+
oneHalfBigDec BigDec = oneBigDec.Quo(twoBigDec)
65+
negOneBigDec BigDec = oneBigDec.Neg()
6166
)
6267

6368
// Decimal errors
@@ -1028,9 +1033,9 @@ func DecApproxEq(t *testing.T, d1 BigDec, d2 BigDec, tol BigDec) (*testing.T, bo
10281033
func (x BigDec) LogBase2() BigDec {
10291034
// create a new decimal to avoid mutating
10301035
// the receiver's int buffer.
1031-
xCopy := ZeroBigDec()
1036+
xCopy := BigDec{}
10321037
xCopy.i = new(big.Int).Set(x.i)
1033-
if xCopy.LTE(ZeroBigDec()) {
1038+
if xCopy.LTE(zeroBigDec) {
10341039
panic(fmt.Sprintf("log is not defined at <= 0, given (%s)", xCopy))
10351040
}
10361041

@@ -1040,18 +1045,18 @@ func (x BigDec) LogBase2() BigDec {
10401045
y := ZeroBigDec()
10411046

10421047
// repeat until: x >= 1.
1043-
for xCopy.LT(OneBigDec()) {
1048+
for xCopy.LT(oneBigDec) {
10441049
xCopy.i.Lsh(xCopy.i, 1)
1045-
y = y.Sub(OneBigDec())
1050+
y.AddMut(negOneBigDec)
10461051
}
10471052

10481053
// repeat until: x < 2.
10491054
for xCopy.GTE(twoBigDec) {
10501055
xCopy.i.Rsh(xCopy.i, 1)
1051-
y = y.Add(OneBigDec())
1056+
y.AddMut(oneBigDec)
10521057
}
10531058

1054-
b := OneBigDec().Quo(twoBigDec)
1059+
b := oneHalfBigDec.Clone()
10551060

10561061
// N.B. At this point x is a positive real number representing
10571062
// mantissa of the log. We estimate it using the following
@@ -1060,10 +1065,10 @@ func (x BigDec) LogBase2() BigDec {
10601065
// This has shown precision of 32 digits relative
10611066
// to Wolfram Alpha in tests.
10621067
for i := 0; i < maxLog2Iterations; i++ {
1063-
xCopy = xCopy.Mul(xCopy)
1068+
xCopy.MulMut(xCopy)
10641069
if xCopy.GTE(twoBigDec) {
10651070
xCopy.i.Rsh(xCopy.i, 1)
1066-
y = y.Add(b)
1071+
y.AddMut(b)
10671072
}
10681073
b.i.Rsh(b.i, 1)
10691074
}

0 commit comments

Comments
 (0)