package indicator import "sig-pub/pkg/types" // MACD 分成: Hist(柱状图), DIF线, DEA(信号线) // 计算 DIF线: 反映短期趋势与长期趋势的“收敛/散度” // MACD: https://www.investopedia.com/terms/m/macd.asp type MACD struct { } func (c *MACD) Meta() IndicatorMeta { return IndicatorMeta{ Name: "MACD", Input: []types.InputArg{ {Name: "fast", Type: types.InputTypeUInt, Desc: "快线周期", Default: 12}, // 12 {Name: "slow", Type: types.InputTypeUInt, Desc: "慢线周期", Default: 26}, // 26 {Name: "singal", Type: types.InputTypeUInt, Desc: "信号线周期", Default: 9}, // 9 }, State: []string{"dif", "dea"}, Plots: []Plot{ {Name: "MACD", State: "vector", Type: PlotHistogram, Props: PlotProps{"color": ColorGreen2}, Exps: []PlotExp{ {Exp: "vector < 0", Props: PlotProps{"color": ColorRed2}}, {Exp: "vector >= 0", Props: PlotProps{"color": ColorGreen2}}, }}, {Name: "DIF线", State: "dif", Type: PlotLine, Props: PlotProps{"color": ColorYellow}}, {Name: "DEA线", State: "dea", Type: PlotLine, Props: PlotProps{"color": ColorRed}}, }, } } func (c *MACD) CandlePeriods(ctx IIndicatorContext) int16 { return max( ctx.Indicator("EMA", ctx.Input().Int16("fast")).CandlePeriods(), ctx.Indicator("EMA", ctx.Input().Int16("slow")).CandlePeriods(), ) + ctx.Input().Int16("singal") + 1 } // Calculate macd计算从第max(fast, slow)期开始稳定 func (c *MACD) Calculate(ctx IIndicatorContext) (vector float64) { fast := ctx.Input().Int16("fast") slow := ctx.Input().Int16("slow") singal := ctx.Input().Int16("singal") // macd dif fastEma := ctx.Indicator("EMA", fast).Get(0) slowEma := ctx.Indicator("EMA", slow).Get(0) macd_dif := fastEma - slowEma ctx.State().Set("dif", macd_dif) // macd dea deaPrev, ok := ctx.State().Get("dea", 1) if !ok { // 初始值前9期的 MACD_DIF SMA difs, ok := ctx.State().Series("dif", 1, singal) if !ok { return } deaPrev = difs.Avg() } // macd hist beta := 2 / float64(singal+1) macd_dea := beta*macd_dif + (1-beta)*deaPrev ctx.State().Set("dea", macd_dea) vector = (macd_dif - macd_dea) * 2 return }