Files
banstagy/ptn/hammer/v5.go
2026-08-24 20:53:21 +08:00

97 lines
2.5 KiB
Go
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

package hammer
import (
"fmt"
"github.com/banbox/banbot/config"
"github.com/banbox/banbot/strat"
"github.com/banbox/banexg"
ta "github.com/banbox/banta"
"math"
)
/*
加入RSI低于55限制,同时调低atr倍率,允许更多机会。
测试效果不如V4,弃用
*/
const (
v5AtrLen = 14
v5WatchMin = 5 // 入场后观察后续蜡烛的最少个数
v5WatchMax = 100 // 入场后观察后续蜡烛的最多个数
v5RefNum = 20 // 回顾历史回撤的数量
)
func makeV5OnBar(atrLen, refNum, watchMin, watchMax int, baseRate float64) func(s *strat.StratJob) {
return func(s *strat.StratJob) {
e := s.Env
ma5 := ta.SMA(e.Close, 5).Get(0)
atr := ta.ATR(e.High, e.Low, e.Close, atrLen)
baseAtrLen := int(math.Round(float64(atrLen) * 4.3))
atrBase := ta.Lowest(ta.Highest(atr, atrLen), baseAtrLen).Get(0)
rsiCol := ta.RSI(e.Close, 20)
rsi, rsiPrv := rsiCol.Get(0), rsiCol.Get(1)
more, _ := s.More.(*MoreHammer)
if math.IsNaN(atrBase) {
return
}
rsiOk := rsiPrv >= 70 && rsiPrv-rsi > 30 || (rsiPrv+rsi)/2 < 55
if !rsiOk {
return
}
o, h, l, c := e.Open.Get(0), e.High.Get(0), e.Low.Get(0), e.Close.Get(0)
v := e.Volume.Get(0)
solid := math.Abs(o - c)
btm := min(o, c) - l
up := h - max(o, c)
if btm > max(2.0*solid, up*5.0, atrBase*baseRate) && c < ma5 {
// 检查是否处于信号后观察模式
CloseWatch(s, more, refNum)
// 开始新观察
bar := &banexg.Kline{Time: e.TimeStart, Open: o, High: h, Low: l, Close: c, Volume: v}
StartWatch(e, more, bar, btm/atrBase)
// 创建入场订单
limit := c - (c-l)*more.backRate*0.55
stopLoss := c - atr.Get(0)*3.0
if stopLoss >= limit {
stopLoss = limit - atr.Get(0)
}
err := s.OpenOrder(&strat.EnterReq{
Tag: "long",
Limit: limit,
StopLoss: stopLoss,
})
if err != nil {
fmt.Printf("open fail %v", err)
}
} else if more.lastEnt > 0 {
// 更新观察数据
UpdateWatch(s, more, c, l, watchMin, watchMax, refNum)
}
}
}
func MainV5(pol *config.RunPolicyConfig) *strat.TradeStrat {
return &strat.TradeStrat{
Version: 1,
WarmupNum: 3000,
MinTfScore: 0.75,
DrawDownExit: true,
StopEnterBars: 10,
OnStartUp: func(s *strat.StratJob) {
s.More = &MoreHammer{
odInfos: map[int64]*OdInfo{},
}
},
OnBar: makeV5OnBar(v5AtrLen, v5RefNum, v5WatchMin, v5WatchMax, 2.2),
OnOrderChange: onOrderChange,
GetDrawDownExitRate: makeDrawDownExit(0.8, [][2]float64{
{0.625, 0.25},
{0.3, 0.37},
{0.15, 0.5},
}),
}
}