2021-05-07 18:09:45 +00:00
|
|
|
package indicator
|
|
|
|
|
|
|
|
import (
|
2022-02-15 05:55:19 +00:00
|
|
|
"encoding/json"
|
2021-05-12 06:39:10 +00:00
|
|
|
"math"
|
2021-05-07 18:09:45 +00:00
|
|
|
"testing"
|
|
|
|
|
2022-02-08 04:41:24 +00:00
|
|
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
2022-02-15 05:55:19 +00:00
|
|
|
"github.com/c9s/bbgo/pkg/types"
|
2021-05-07 18:09:45 +00:00
|
|
|
)
|
2022-02-15 05:55:19 +00:00
|
|
|
|
2021-05-07 18:09:45 +00:00
|
|
|
func Test_calculateVWAP(t *testing.T) {
|
2022-03-28 19:19:29 +00:00
|
|
|
var trivialPrices = []byte(`[0]`)
|
|
|
|
var trivialVolumes = []byte(`[1]`)
|
|
|
|
var easyPrices = []byte(`[1, 2, 3]`)
|
|
|
|
var easyVolumes = []byte(`[4, 5, 6]`)
|
|
|
|
var windowPrices = []byte(`[1, 2, 3, 4]`)
|
|
|
|
var windowVolumes = []byte(`[4, 5, 6, 7]`)
|
|
|
|
var randomPrices = []byte(`[0.6046702879796195, 0.9405190880450124, 0.6645700532184904, 0.4377241871869802, 0.4246474970712657, 0.6868330728671094, 0.06564701921747622, 0.15652925473279125, 0.09697951891448456, 0.3009218605852871]`)
|
|
|
|
var randomVolumes = []byte(`[0.5152226285020653, 0.8136499609900968, 0.21427387258237493, 0.380667189299686, 0.31806817433032986, 0.4688998449024232, 0.2830441511804452, 0.2931118573368158, 0.6790946759202162, 0.2185630525927643]`)
|
|
|
|
|
2022-02-08 04:41:24 +00:00
|
|
|
buildKLines := func(pb, vb []byte) (kLines []types.KLine) {
|
|
|
|
var prices, volumes []fixedpoint.Value
|
|
|
|
_ = json.Unmarshal(pb, &prices)
|
|
|
|
_ = json.Unmarshal(vb, &volumes)
|
2021-05-07 18:09:45 +00:00
|
|
|
for i, p := range prices {
|
|
|
|
kLines = append(kLines, types.KLine{High: p, Low: p, Close: p, Volume: volumes[i]})
|
|
|
|
}
|
|
|
|
return kLines
|
|
|
|
}
|
|
|
|
|
|
|
|
tests := []struct {
|
|
|
|
name string
|
|
|
|
kLines []types.KLine
|
|
|
|
window int
|
|
|
|
want float64
|
|
|
|
}{
|
|
|
|
{
|
|
|
|
name: "trivial_case",
|
2022-02-08 04:41:24 +00:00
|
|
|
kLines: buildKLines(trivialPrices, trivialVolumes),
|
2021-05-07 18:09:45 +00:00
|
|
|
window: 0,
|
|
|
|
want: 0.0,
|
|
|
|
},
|
|
|
|
{
|
|
|
|
name: "easy_case",
|
2022-02-08 04:41:24 +00:00
|
|
|
kLines: buildKLines(easyPrices, easyVolumes),
|
2021-05-07 18:09:45 +00:00
|
|
|
window: 0,
|
|
|
|
want: (1*4 + 2*5 + 3*6) / float64(4+5+6),
|
|
|
|
},
|
|
|
|
{
|
|
|
|
name: "window_case",
|
2022-02-08 04:41:24 +00:00
|
|
|
kLines: buildKLines(windowPrices, windowVolumes),
|
2021-05-07 18:09:45 +00:00
|
|
|
window: 3,
|
|
|
|
want: (2*5 + 3*6 + 4*7) / float64(5+6+7),
|
|
|
|
},
|
|
|
|
{
|
|
|
|
name: "random_case",
|
|
|
|
kLines: buildKLines(randomPrices, randomVolumes),
|
|
|
|
window: 0,
|
|
|
|
want: 0.48727133857423566,
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
|
|
|
for _, tt := range tests {
|
|
|
|
t.Run(tt.name, func(t *testing.T) {
|
2023-07-10 08:54:22 +00:00
|
|
|
priceF := types.KLineTypicalPriceMapper
|
2022-07-13 17:12:36 +00:00
|
|
|
got := calculateVWAP(tt.kLines, priceF, tt.window)
|
2021-05-12 06:39:10 +00:00
|
|
|
diff := math.Trunc((got-tt.want)*100) / 100
|
|
|
|
if diff != 0 {
|
2021-05-07 18:09:45 +00:00
|
|
|
t.Errorf("calculateVWAP() = %v, want %v", got, tt.want)
|
|
|
|
}
|
|
|
|
})
|
|
|
|
}
|
|
|
|
}
|