bbgo_origin/pkg/indicator/v2/cross.go

61 lines
1.0 KiB
Go
Raw Permalink Normal View History

2023-07-10 08:54:22 +00:00
package indicatorv2
2023-06-04 06:47:29 +00:00
import (
"github.com/c9s/bbgo/pkg/datatype/floats"
2023-07-10 08:54:22 +00:00
"github.com/c9s/bbgo/pkg/types"
2023-06-04 06:47:29 +00:00
)
type CrossType float64
const (
CrossOver CrossType = 1.0
CrossUnder CrossType = -1.0
)
// CrossStream subscribes 2 upstreams, and calculate the cross signal
type CrossStream struct {
2023-07-10 08:54:22 +00:00
*types.Float64Series
2023-06-04 06:47:29 +00:00
a, b floats.Slice
}
// Cross creates the CrossStream object:
//
// cross := Cross(fastEWMA, slowEWMA)
2023-07-10 08:54:22 +00:00
func Cross(a, b types.Float64Source) *CrossStream {
2023-06-04 06:47:29 +00:00
s := &CrossStream{
2023-07-10 08:54:22 +00:00
Float64Series: types.NewFloat64Series(),
2023-06-04 06:47:29 +00:00
}
a.OnUpdate(func(v float64) {
s.a.Push(v)
s.calculate()
})
b.OnUpdate(func(v float64) {
s.b.Push(v)
s.calculate()
})
return s
}
func (s *CrossStream) calculate() {
if s.a.Length() != s.b.Length() {
return
}
current := s.a.Last(0) - s.b.Last(0)
previous := s.a.Last(1) - s.b.Last(1)
if previous == 0.0 {
return
}
// cross over or cross under
if current*previous < 0 {
if current > 0 {
s.PushAndEmit(float64(CrossOver))
} else {
s.PushAndEmit(float64(CrossUnder))
}
}
}