From 89aa63dd643e0b2abbbfe4d22d7cba8f8169cf4d Mon Sep 17 00:00:00 2001 From: c9s Date: Mon, 29 May 2023 17:12:34 +0800 Subject: [PATCH] floats: add floats LSM --- pkg/datatype/floats/funcs_test.go | 6 ++++++ pkg/datatype/floats/pivot.go | 4 ++-- pkg/datatype/floats/slice.go | 27 +++++++++++++++++++++++++++ 3 files changed, 35 insertions(+), 2 deletions(-) diff --git a/pkg/datatype/floats/funcs_test.go b/pkg/datatype/floats/funcs_test.go index 25c37f908..52401fbd4 100644 --- a/pkg/datatype/floats/funcs_test.go +++ b/pkg/datatype/floats/funcs_test.go @@ -15,3 +15,9 @@ func TestHigher(t *testing.T) { out := Higher([]float64{10.0, 11.0, 12.0, 13.0, 15.0}, 12.0) assert.Equal(t, []float64{13.0, 15.0}, out) } + +func TestLSM(t *testing.T) { + slice := Slice{1., 2., 3., 4.} + slope := LSM(slice) + assert.Equal(t, 1.0, slope) +} diff --git a/pkg/datatype/floats/pivot.go b/pkg/datatype/floats/pivot.go index f79403047..b7536cbe3 100644 --- a/pkg/datatype/floats/pivot.go +++ b/pkg/datatype/floats/pivot.go @@ -1,10 +1,10 @@ package floats func (s Slice) Pivot(left, right int, f func(a, pivot float64) bool) (float64, bool) { - return CalculatePivot(s, left, right, f) + return FindPivot(s, left, right, f) } -func CalculatePivot(values Slice, left, right int, f func(a, pivot float64) bool) (float64, bool) { +func FindPivot(values Slice, left, right int, f func(a, pivot float64) bool) (float64, bool) { length := len(values) if right == 0 { diff --git a/pkg/datatype/floats/slice.go b/pkg/datatype/floats/slice.go index 40b3a427b..f9efa2d6c 100644 --- a/pkg/datatype/floats/slice.go +++ b/pkg/datatype/floats/slice.go @@ -187,3 +187,30 @@ func (s Slice) Index(i int) float64 { func (s Slice) Length() int { return len(s) } + +func (s Slice) LSM() float64 { + return LSM(s) +} + +func LSM(values Slice) float64 { + var sumX, sumY, sumXSqr, sumXY = .0, .0, .0, .0 + + end := len(values) - 1 + for i := end; i >= 0; i-- { + val := values[i] + per := float64(end - i + 1) + sumX += per + sumY += val + sumXSqr += per * per + sumXY += val * per + } + + length := float64(len(values)) + slope := (length*sumXY - sumX*sumY) / (length*sumXSqr - sumX*sumX) + + average := sumY / length + tail := average - slope*sumX/length + slope + head := tail + slope*(length-1) + slope2 := (tail - head) / (length - 1) + return slope2 +}