定量的な傾向追跡戦略

作者: リン・ハーンチャオチャン,日付: 2024-02-01 11:42:22
タグ:

img

概要

この戦略は,市場動向を判断するためにボリンジャーバンド,RSI,ADX,MACDなどの複数の指標を採用し,強力なトレンド識別能力を備えています.指標信号が同時に上昇しているときにトレンドフォロー戦略を採用します.指標信号が同時に下落しているときにストップロスをするためにポジションを閉じます.

戦略原則

  • トレンドが形成されるかどうかを判断するために,価格が上方または下部レールに近いかどうかを判断するためにボリンジャーバンドを使用します.
  • 誤ったブレイクを防ぐために,過剰購入と過剰販売領域を避けるために,RSI指標と組み合わせる.
  • ADX を使ってトレンド強さを決定し,トレンド強さが強いときにのみ信号を出す.
  • 短期および長期動向の一貫性を判断するためにMACDを採用する
  • オブナイトリスクを回避するために,取引セッションを制限する

複数の指標の組み合わせによる判断により 価格動向を正確に特定し 傾向が発生したときに 適切なタイミングで追跡し 過剰な利益を得ることができます

利点分析

この戦略の最大の利点は,指標組み合わせの判断がより包括的で正確であり,価格動向を効果的に特定し,単一の指標による誤った信号を回避できるということです.

具体的には以下のような利点があります

  1. ボリンジャー・バンドは価格変動の範囲と強さを決定することができます
  2. RSIは過買いエリアで購入し,過売りエリアで販売することを避ける
  3. ADXはトレンド強さを決定し,強いトレンドのみを追います
  4. MACDは短期と長期間の一貫性を判断する
  5. オブナイトリスクを回避するための取引セッションの制限

インディケーターの組み合わせを判断することで 誤った信号を最大限に抑え 戦略の安定性を高めることができます

リスク分析

この戦略の主なリスクは以下のものです.

  1. 指標の不具合の原因となる市場イベント
  2. 範囲限定市場における誤った信号の頻度

リスク1については,複数の指標に頼ることで,単一の指標の失敗の問題をある程度軽減できますが,リスク管理メカニズムはまだ改善する必要があります.

リスク2のパラメータは,取引範囲が狭くなり,リスクを軽減するために取引頻度を減らすために適切に調整できます.

オプティマイゼーションの方向性

この戦略の最適化可能な主な側面は以下の通りである.

  1. トレイリングストップ損失,タイムストップ損失,ブレイクストップ損失など,ストップ損失メカニズムを追加し,あまりにも深く引き戻すことを避ける.
  2. パラメータを最適化,インジケーターのパラメータを調整
  3. 音量フィルターなどのフィルターを追加して,低音量で誤ったブレイクを避ける
  4. KDJ,OBVなどのインジケーターを追加して信号の精度を向上させる
  5. パラメータを自動最適化するための機械学習方法を採用する

継続的な最適化によって,パラメータの安定性を継続的に改善し,誤った信号の確率を減らす.

概要

この戦略は,指標の組み合わせによる判断によって,価格動向を効果的に特定できる傾向信号を特定する比較的強い能力を持っています.

しかし,リスク管理やパラメータ最適化も一定リスクがあり,安定した長期運用のために継続的に改善する必要がある.機械学習のような方法が後に導入され,パラメータの自動最適化を達成できれば,戦略の強さと収益性が大幅に向上する.


/*backtest
start: 2024-01-01 00:00:00
end: 2024-01-31 00:00:00
period: 5h
basePeriod: 15m
exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT"}]
*/

// This source code is subject to the terms of the Mozilla Public License 2.0 at https://mozilla.org/MPL/2.0/
// © abilash.s.90


dIMinusCalc(adxLen) =>
    
    smoothedTrueRange = 0.0
    smoothedDirectionalMovementMinus = 0.0
    dIMinus = 0.0
    trueRange = 0.0
    directionalMovementMinus = 0.0
    
    trueRange := max(max(high-low, abs(high-nz(close[1]))), abs(low-nz(close[1])))
    directionalMovementMinus := nz(low[1])-low > high-nz(high[1]) ? max(nz(low[1])-low, 0): 0
    
    smoothedTrueRange := nz(smoothedTrueRange[1]) - (nz(smoothedTrueRange[1])/adxLen) + trueRange
    smoothedDirectionalMovementMinus := nz(smoothedDirectionalMovementMinus[1]) - (nz(smoothedDirectionalMovementMinus[1])/adxLen) + directionalMovementMinus
    
    dIMinus := smoothedDirectionalMovementMinus / smoothedTrueRange * 100
    
    dIMinus

dIPlusCalc(adxLen) =>
    
    smoothedTrueRange = 0.0
    smoothedDirectionalMovementPlus = 0.0
    dIPlus =  0.0
    trueRange = 0.0
    directionalMovementPlus = 0.0
    
    trueRange := max(max(high-low, abs(high-nz(close[1]))), abs(low-nz(close[1])))
    directionalMovementPlus := high-nz(high[1]) > nz(low[1])-low ? max(high-nz(high[1]), 0): 0
    
    smoothedTrueRange := nz(smoothedTrueRange[1]) - (nz(smoothedTrueRange[1])/adxLen) + trueRange
    smoothedDirectionalMovementPlus := nz(smoothedDirectionalMovementPlus[1]) - (nz(smoothedDirectionalMovementPlus[1])/adxLen) + directionalMovementPlus
    
    dIPlus := smoothedDirectionalMovementPlus / smoothedTrueRange * 100
    
    dIPlus
    
    
Adx(adxLen) =>
    dIPlus =  0.0
    dIMinus = 0.0
    dX = 0.0
    aDX = 0.0
    dIPlus := dIPlusCalc(adxLen)
    dIMinus := dIMinusCalc(adxLen)
    dX := abs(dIPlus-dIMinus) / (dIPlus+dIMinus)*100
    aDX := sma(dX, adxLen)
    
    aDX
    
BarInSession(sess) => time(timeframe.period, sess) != 0


//@version=4
strategy("Bollinger Band + RSI + ADX + MACD", overlay=true)

//Session

session = input(title="Trading Session", type=input.session, defval="0930-1500")

sessionColor = BarInSession(session) ? color.green : na

bgcolor(color=sessionColor, transp=95)

// Bollinger Bands
src = input(high, title="Bollinger Band Source", type=input.source)
length = input(3, minval=1, type=input.integer, title="Bollinger Band Length")
mult = input(4.989, minval=0.001, maxval=50, step=0.001, type=input.float, title="Bollinger Band Std Dev")
basis = sma(src, length)
dev = mult * stdev(src, length)
upper = basis + dev
lower = basis - dev


plot(upper, title="Bollinger Band Upper", color=color.red)
plot(lower, title="Bollinger Band Lower", color=color.green)

// RSI
rsiSrc = input(close, title="RSI Source", type=input.source)
rsiLength = input(16, minval=1, type=input.integer, title="RSI Length")
rsiComparator = input(39.2, title="RSI Comparator", type=input.float, step=0.1)

rsi = rsi(rsiSrc, rsiLength)

// ADX
adxLength = input(14, minval=1, type=input.integer, title="ADX Length")
adxComparator = input(14, minval=1, type=input.integer, title="ADX Comparator")

adx = Adx(adxLength)

// Heikinashi

haClose = security(heikinashi(syminfo.ticker), timeframe.period, close)
haOpen = security(heikinashi(syminfo.ticker), timeframe.period, open)

nextHaOpen = (haOpen + haClose) / 2

//MACD

macdCalcTypeProcessed = input(title="MACD Source", type=input.source, defval=high)
fast = input(12, title="MACD Fast")
slow = input(20, title="MACD Slow")
signalLen = input(15, title="MACD Signal")

fastMA = ema(macdCalcTypeProcessed, fast)
slowMA = ema(macdCalcTypeProcessed, slow)
macd = fastMA - slowMA
signal = sma(macd, signalLen)



longCondition() =>
    (low < lower) and (rsi[0] > rsiComparator) and (adx > adxComparator) and (close > nextHaOpen) and BarInSession(session) and macd > signal

stop = (close - max((low - (low * 0.0022)), (close - (close * 0.0032)))) / syminfo.mintick
target = (max(upper, (close + (close * 0.0075))) - close) / syminfo.mintick


strategy.entry("SX,LE", strategy.long, when=longCondition(), comment="SX,LE")
strategy.close_all(when=(not BarInSession(session)))
strategy.exit("LX", from_entry="SX,LE", profit=target, loss=stop)


もっと