From 76aa4ff34af0e15a45421e7d2018e46ef2854790 Mon Sep 17 00:00:00 2001 From: Bel LaPointe Date: Wed, 25 Oct 2023 19:19:07 -0600 Subject: [PATCH] wip --- ledger/predict.go | 68 +++++++++++++++++++++++++++++++++++++++++ ledger/predict_test.go | 61 ++++++++++++++++++++++++++++++++++++ ledger/register.go | 28 ----------------- ledger/register_test.go | 31 ------------------- 4 files changed, 129 insertions(+), 59 deletions(-) create mode 100644 ledger/predict.go create mode 100644 ledger/predict_test.go delete mode 100644 ledger/register.go delete mode 100644 ledger/register_test.go diff --git a/ledger/predict.go b/ledger/predict.go new file mode 100644 index 0000000..32e693d --- /dev/null +++ b/ledger/predict.go @@ -0,0 +1,68 @@ +package ledger + +import ( + "fmt" + "io" + "log" + "maps" + "time" +) + +func RegisterWithContributionPrediction(reg map[string]Balances, windowAsPercentOfTotalDuration float64) (map[string]Balances, error) { + return reg, io.EOF +} + +func BPIWithFixedGrowthPrediction(reg map[string]Balances, windowAsPercentOfTotalDuration float64, pattern string, rate float64) (map[string]Balances, error) { + result := make(map[string]Balances) + return result, io.EOF +} + +func RegisterWithCompoundingInterestPrediction(reg map[string]Balances, windowAsPercentOfTotalDuration float64, pattern string, rate float64) (map[string]Balances, error) { + nameToLastDate := func() map[string]string { + result := map[string]string{} + for date, balances := range reg { + for name := range balances { + if result[name] < date { + result[name] = date + } + } + } + return result + }() + firstTime, lastTime := func() (time.Time, time.Time) { + var latest time.Time + first := time.Now() + for _, v := range nameToLastDate { + v2, _ := dateToTime(v) + if latest.Before(v2) { + latest = v2 + } + if first.Before(v2) { + first = v2 + } + } + return first, latest + }() + log.Println("first", firstTime, "last time", lastTime, "nameToDate", nameToLastDate) + + lastPrediction := lastTime + for lastPrediction.Before(lastTime.Add(lastTime.Sub(firstTime) * time.Duration(windowAsPercentOfTotalDuration))) { + lastPrediction = lastPrediction.Add(time.Hour * 24 * (45 - lastPrediction.Day())) + TODO ^ + } + + result := maps.Clone(reg) + return result, io.EOF +} + +func dateToTime(s string) (time.Time, error) { + for _, layout := range []string{ + "2006-01-02", + "2006-01", + } { + if t, err := time.ParseInLocation(layout, s, time.Local); err == nil { + return t, err + } + } + return time.Time{}, fmt.Errorf("no layout matching %q", s) +} diff --git a/ledger/predict_test.go b/ledger/predict_test.go new file mode 100644 index 0000000..158d996 --- /dev/null +++ b/ledger/predict_test.go @@ -0,0 +1,61 @@ +package ledger + +import ( + "testing" +) + +func TestRegisterPrediction(t *testing.T) { + t.Run("contribution", func(t *testing.T) { + input := newTestRegister() + + got, err := RegisterWithContributionPrediction(input, .12) + if err != nil { + t.Fatal(err) + } + t.Logf("%+v", got) + + if len(got) != len(input)+1 { + t.Error(len(got)) + } + if _, ok := got["2001-11"]; !ok { + t.Error(ok) + } + t.Error("not impl") + }) + + t.Run("compounding interest", func(t *testing.T) { + input := newTestRegister() + + got, err := RegisterWithCompoundingInterestPrediction(input, 1, "X", .04) + if err != nil { + t.Fatal(err) + } + t.Logf("%+v", got) + + if len(got) <= len(input) { + t.Error(len(got)) + } + t.Error("not impl") + }) +} + +func TestBPIPrediction(t *testing.T) { + t.Run("fixed growth", func(t *testing.T) { + t.Error("not impl") + }) +} + +func newTestRegister() map[string]Balances { + return map[string]Balances{ + "2001-01": Balances{"X": Balance{USD: 1}}, + "2001-02": Balances{"X": Balance{USD: 2}}, + "2001-03": Balances{"X": Balance{USD: 3}}, + "2001-04": Balances{"X": Balance{USD: 4}}, + "2001-05": Balances{"X": Balance{USD: 5}}, + "2001-06": Balances{"X": Balance{USD: 6}}, + "2001-07": Balances{"X": Balance{USD: 8}}, + "2001-08": Balances{"X": Balance{USD: 10}}, + "2001-09": Balances{"X": Balance{USD: 12}}, + "2001-10": Balances{"X": Balance{USD: 16}}, + } +} diff --git a/ledger/register.go b/ledger/register.go deleted file mode 100644 index cc84b7f..0000000 --- a/ledger/register.go +++ /dev/null @@ -1,28 +0,0 @@ -package ledger - -import ( - "fmt" - "io" - "time" -) - -func RegisterWithContributionPrediction(reg map[string]Balances, windowAsPercentOfTotalDuration float64) (map[string]Balances, error) { - return reg, io.EOF -} - -func RegisterWithCompoundingInterestPrediction(reg map[string]Balances, windowAsPercentOfTotalDuration float64, name string, rate float64) (map[string]Balances, error) { - result := make(map[string]Balances) - return result, io.EOF -} - -func dateToTime(s string) (time.Time, error) { - for _, layout := range []string{ - "2006-01-02", - "2006-01", - } { - if t, err := time.ParseInLocation(layout, s, time.Local); err == nil { - return t, err - } - } - return time.Time{}, fmt.Errorf("no layout matching %q", s) -} diff --git a/ledger/register_test.go b/ledger/register_test.go deleted file mode 100644 index 775bc95..0000000 --- a/ledger/register_test.go +++ /dev/null @@ -1,31 +0,0 @@ -package ledger - -import ( - "testing" -) - -func TestRegisterPredictContribution(t *testing.T) { - input := map[string]Balances{ - "2001-01": Balances{"X": Balance{USD: 1}}, - "2001-02": Balances{"X": Balance{USD: 2}}, - "2001-03": Balances{"X": Balance{USD: 3}}, - "2001-04": Balances{"X": Balance{USD: 4}}, - "2001-05": Balances{"X": Balance{USD: 5}}, - "2001-06": Balances{"X": Balance{USD: 6}}, - "2001-07": Balances{"X": Balance{USD: 8}}, - "2001-08": Balances{"X": Balance{USD: 10}}, - "2001-09": Balances{"X": Balance{USD: 12}}, - "2001-10": Balances{"X": Balance{USD: 16}}, - } - got, err := RegisterWithContributionPrediction(input, .12) - if err != nil { - t.Fatal(err) - } - if len(got) != len(input)+1 { - t.Error(len(got)) - } - if _, ok := got["2001-11"]; !ok { - t.Error(ok) - } - t.Logf("%+v", got) -}