Bel LaPointe 2023-10-25 19:19:07 -06:00
parent f49308d4d5
commit 76aa4ff34a
4 changed files with 129 additions and 59 deletions

68
ledger/predict.go Normal file
View File

@ -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)
}

61
ledger/predict_test.go Normal file
View File

@ -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}},
}
}

View File

@ -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)
}

View File

@ -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)
}