mirror of
https://github.com/c9s/bbgo.git
synced 2024-11-21 22:43:52 +00:00
pivotshort: improve price grouping
This commit is contained in:
parent
f940bb8e0a
commit
1e8ac0d08a
|
@ -54,6 +54,7 @@ exchangeStrategies:
|
|||
|
||||
# minDistance is used to ignore the place that is too near to the current price
|
||||
minDistance: 3%
|
||||
groupDistance: 1%
|
||||
|
||||
# ratio is the ratio of the resistance price,
|
||||
# higher the ratio, lower the price
|
||||
|
|
|
@ -106,7 +106,6 @@ func (s *BreakLow) Bind(session *bbgo.ExchangeSession, orderExecutor *bbgo.Gener
|
|||
|
||||
// we need the price cross the break line or we do nothing
|
||||
if !(openPrice.Compare(breakPrice) > 0 && closePrice.Compare(breakPrice) < 0) {
|
||||
log.Infof("%s kline is not between the break low price %f", kline.Symbol, breakPrice.Float64())
|
||||
return
|
||||
}
|
||||
|
||||
|
|
|
@ -17,11 +17,12 @@ type ResistanceShort struct {
|
|||
|
||||
types.IntervalWindow
|
||||
|
||||
MinDistance fixedpoint.Value `json:"minDistance"`
|
||||
NumLayers int `json:"numLayers"`
|
||||
LayerSpread fixedpoint.Value `json:"layerSpread"`
|
||||
Quantity fixedpoint.Value `json:"quantity"`
|
||||
Ratio fixedpoint.Value `json:"ratio"`
|
||||
MinDistance fixedpoint.Value `json:"minDistance"`
|
||||
GroupDistance fixedpoint.Value `json:"groupDistance"`
|
||||
NumLayers int `json:"numLayers"`
|
||||
LayerSpread fixedpoint.Value `json:"layerSpread"`
|
||||
Quantity fixedpoint.Value `json:"quantity"`
|
||||
Ratio fixedpoint.Value `json:"ratio"`
|
||||
|
||||
session *bbgo.ExchangeSession
|
||||
orderExecutor *bbgo.GeneralOrderExecutor
|
||||
|
@ -39,6 +40,10 @@ func (s *ResistanceShort) Bind(session *bbgo.ExchangeSession, orderExecutor *bbg
|
|||
s.activeOrders = bbgo.NewActiveOrderBook(s.Symbol)
|
||||
s.activeOrders.BindStream(session.UserDataStream)
|
||||
|
||||
if s.GroupDistance.IsZero() {
|
||||
s.GroupDistance = fixedpoint.NewFromFloat(0.01)
|
||||
}
|
||||
|
||||
store, _ := session.MarketDataStore(s.Symbol)
|
||||
|
||||
s.resistancePivot = &indicator.Pivot{IntervalWindow: s.IntervalWindow}
|
||||
|
@ -65,13 +70,12 @@ func (s *ResistanceShort) Bind(session *bbgo.ExchangeSession, orderExecutor *bbg
|
|||
|
||||
func (s *ResistanceShort) findNextResistancePriceAndPlaceOrders(closePrice fixedpoint.Value) {
|
||||
// if the close price is still lower than the resistance price, then we don't have to update
|
||||
if closePrice.Compare(s.nextResistancePrice) <= 0 {
|
||||
if closePrice.Compare(s.nextResistancePrice.Mul(one.Add(s.Ratio))) <= 0 {
|
||||
return
|
||||
}
|
||||
|
||||
minDistance := s.MinDistance.Float64()
|
||||
lows := s.resistancePivot.Lows
|
||||
resistancePrices := findPossibleResistancePrices(closePrice.Float64(), minDistance, lows)
|
||||
resistancePrices := findPossibleResistancePrices(closePrice.Float64()*(1.0+minDistance), s.GroupDistance.Float64(), s.resistancePivot.Lows)
|
||||
|
||||
log.Infof("last price: %f, possible resistance prices: %+v", closePrice.Float64(), resistancePrices)
|
||||
|
||||
|
@ -151,51 +155,68 @@ func (s *ResistanceShort) placeResistanceOrders(ctx context.Context, resistanceP
|
|||
}
|
||||
|
||||
func findPossibleSupportPrices(closePrice float64, minDistance float64, lows []float64) []float64 {
|
||||
// sort float64 in increasing order
|
||||
// lower to higher prices
|
||||
sort.Float64s(lows)
|
||||
return group(lower(lows, closePrice), minDistance)
|
||||
}
|
||||
|
||||
var supportPrices []float64
|
||||
var last = closePrice
|
||||
for i := len(lows) - 1; i >= 0; i-- {
|
||||
price := lows[i]
|
||||
func lower(arr []float64, x float64) []float64 {
|
||||
sort.Float64s(arr)
|
||||
|
||||
var rst []float64
|
||||
for _, a := range arr {
|
||||
// filter prices that are lower than the current closed price
|
||||
if price > closePrice {
|
||||
if a > x {
|
||||
continue
|
||||
}
|
||||
|
||||
if (price / last) < (1.0 - minDistance) {
|
||||
continue
|
||||
}
|
||||
|
||||
supportPrices = append(supportPrices, price)
|
||||
last = price
|
||||
rst = append(rst, a)
|
||||
}
|
||||
|
||||
return supportPrices
|
||||
return rst
|
||||
}
|
||||
|
||||
func higher(arr []float64, x float64) []float64 {
|
||||
sort.Float64s(arr)
|
||||
|
||||
var rst []float64
|
||||
for _, a := range arr {
|
||||
// filter prices that are lower than the current closed price
|
||||
if a < x {
|
||||
continue
|
||||
}
|
||||
rst = append(rst, a)
|
||||
}
|
||||
|
||||
return rst
|
||||
}
|
||||
|
||||
func group(arr []float64, minDistance float64) []float64 {
|
||||
var groups []float64
|
||||
var grp = []float64{arr[0]}
|
||||
for _, price := range arr {
|
||||
avg := average(grp)
|
||||
if (price / avg) > (1.0 + minDistance) {
|
||||
groups = append(groups, avg)
|
||||
grp = []float64{price}
|
||||
} else {
|
||||
grp = append(grp, price)
|
||||
}
|
||||
}
|
||||
|
||||
if len(grp) > 0 {
|
||||
groups = append(groups, average(grp))
|
||||
}
|
||||
|
||||
return groups
|
||||
}
|
||||
|
||||
func findPossibleResistancePrices(closePrice float64, minDistance float64, lows []float64) []float64 {
|
||||
// sort float64 in increasing order
|
||||
// lower to higher prices
|
||||
sort.Float64s(lows)
|
||||
|
||||
var resistancePrices []float64
|
||||
var last = closePrice
|
||||
for _, price := range lows {
|
||||
// filter prices that are lower than the current closed price
|
||||
if price < closePrice {
|
||||
continue
|
||||
}
|
||||
|
||||
if (price / last) < (1.0 + minDistance) {
|
||||
continue
|
||||
}
|
||||
|
||||
resistancePrices = append(resistancePrices, price)
|
||||
last = price
|
||||
}
|
||||
|
||||
return resistancePrices
|
||||
return group(higher(lows, closePrice), minDistance)
|
||||
}
|
||||
|
||||
func average(arr []float64) float64 {
|
||||
s := 0.0
|
||||
for _, a := range arr {
|
||||
s += a
|
||||
}
|
||||
return s / float64(len(arr))
|
||||
}
|
||||
|
|
28
pkg/strategy/pivotshort/resistance_test.go
Normal file
28
pkg/strategy/pivotshort/resistance_test.go
Normal file
|
@ -0,0 +1,28 @@
|
|||
package pivotshort
|
||||
|
||||
import (
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/assert"
|
||||
)
|
||||
|
||||
func Test_findPossibleResistancePrices(t *testing.T) {
|
||||
prices := findPossibleResistancePrices(19000.0, 0.01, []float64{
|
||||
23020.0,
|
||||
23040.0,
|
||||
23060.0,
|
||||
|
||||
24020.0,
|
||||
24040.0,
|
||||
24060.0,
|
||||
})
|
||||
assert.Equal(t, []float64{23035, 24040}, prices)
|
||||
|
||||
|
||||
prices = findPossibleResistancePrices(19000.0, 0.01, []float64{
|
||||
23020.0,
|
||||
23040.0,
|
||||
23060.0,
|
||||
})
|
||||
assert.Equal(t, []float64{23035}, prices)
|
||||
}
|
Loading…
Reference in New Issue
Block a user