この記事では,グラフリングパターンを介して収益性の高い機会を特定し,移動平均値との価格クロスオーバーをエントリー信号として使用するアルゴリズム取引戦略を紹介しています.この戦略は,技術分析とトレンドフォロー方法を組み合わせて,統合とトレンド逆転点で利益を得ることを目指しています.
この戦略の基本的な論理は,関係のない2つの指標の収束に基づいています.
飲み込むパターン: 2本のろうそくの逆転パターンで,第2のろうそくの体は完全に第1のろうそくの体を飲み込む.逆転の機会を特定するために使用される.
移動平均線との価格クロスオーバー:価格が下から移動平均線を越えると購入信号が生成される.価格が上から移動平均線を越えると販売信号が生成される.
潜在的市場逆転のタイミングを,包括的なパターンで判断し,移動平均値と価格クロスオーバーを確認信号として利用することで,利益を得る確率が向上することができる.
具体的には,この戦略は,3つの種類の浸透パターン - 上昇,下落,影を浸透させない - を追跡し,潜在的な統合と逆転を決定します.価格と移動平均のクロスオーバーの黄金十字とデッドクロス信号とともに,オープンポジションの方向性が最終的に決定されます.
この戦略の最大の利点は,決定の有効性を向上させるために関係のない指標の収束を利用することです. 吸収パターンは市場の逆転のタイミングと確率を判断し,移動平均との価格クロスオーバーは逆転の方向性と勢いを検証します. 両者は互いを検証し,誤った信号による取引損失を効果的に削減することができます.
また,パラメータ設定の柔軟性にも利点があります.ユーザーは移動平均期とストップ損失範囲などのパラメータを設定して戦略を最適化することができます.
複数の指標を使用することで判断が改善されるが,この戦略では依然として誤った信号のリスクがある. 吸収パターンは100%信頼性の高い逆転信号ではない. また,移動平均値との価格クロスオーバーでも失敗シナリオが存在している. これらはすべて,早期開設ポジションによる損失につながる可能性がある.
さらに,ほとんどの技術分析戦略と同様に,範囲と統合などの競合するトレンド市場でも不良なパフォーマンスを発揮する.長期的横向価格アクションはストップ損失を誘発したり,利益獲得スペースを制限したりする.
リスク制御のために,移動平均期とストップ損失範囲などのパラメータを相応に調整することができる.他の指標も,動向や横向市場を特定するために考慮することができるので,戦略参加は動的に管理することができます.
この戦略では,以下の分野を最適化できます.
適正なパラメータセットを見つけるために,より多くの移動平均タイプをテストします. 例えば,重度の移動平均,二重スムーズ移動平均など.
横向市場でのポジション開設を避けるためにトレンド判断指標を追加します.例はADX,ボリンジャーバンドなどです.
効果を高めるためにストップ損失方法を最適化する.ストップ損失を後押しする,チェンデリア出口は検討できる.
ろうそくのパターンを判断する機械学習方法を増やし 飲み込む認識の精度を向上させる
適応調整のためのパラメータ最適化機能を追加します.
この戦略は,逆転のタイミングをエングロフィングパターンで特定し,移動平均値との価格クロスオーバーを使用して方向性を検証する.指標の収束を通じて意思決定の有効性を向上させることで,技術分析アプローチである.利点には補完指標と柔軟なパラメータが含まれます.欠点は誤った信号のリスクと横向市場における弱さです.この戦略をさらに強化する方法には,移動平均パラメータを最適化すること,ストップ損失方法,トレンドフィルタリング指標を追加することなどが含まれます.
/*backtest start: 2023-12-30 00:00:00 end: 2024-01-29 00:00:00 period: 3h basePeriod: 15m exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT"}] */ //@version=4 //@author=Daveatt StrategyName = "BEST Engulfing + MA" ShortStrategyName = "BEST Engulfing + MA" strategy(title=StrategyName, shorttitle=ShortStrategyName, overlay=true) includeEngulfing = true includeMA = true source_ma = input(title="Source Price vs MA", type=input.source, defval=close) typeofMA = input(title="Type of MA", defval="SMA", options=["RMA", "SMA", "EMA", "WMA", "VWMA", "SMMA", "KMA", "TMA", "HullMA", "DEMA", "TEMA"]) length_ma = input(32, title = "MA Length", type=input.integer) // ---------- Candle components and states GreenCandle = close > open RedCandle = close < open NoBody = close==open Body = abs(close-open) // bullish conditions isBullishEngulfing1 = max(close[1],open[1]) < max(close,open) and min(close[1],open[1]) > min(close,open) and Body > Body[1] and GreenCandle and RedCandle[1] isBullishEngulfing2 = max(close[1],open[1]) < max(close,open) and min(close[1],open[1]) <= min(close,open) and Body > Body[1] and GreenCandle and RedCandle[1] // bearish conditions isBearishEngulfing1 = max(close[1],open[1]) < max(close,open) and min(close[1],open[1]) > min(close,open) and Body > Body[1] and RedCandle and GreenCandle[1] isBearishEngulfing2 = max(close[1],open[1]) >= max(close,open) and min(close[1],open[1]) > min(close,open) and Body > Body[1] and RedCandle and GreenCandle[1] // consolidation of conditions isBullishEngulfing = isBullishEngulfing1 or isBullishEngulfing2 isBearishEngulfing = isBearishEngulfing1 or isBearishEngulfing2 //isBullishEngulfing = max(close[1],open[1]) < max(close,open) and min(close[1],open[1]) > min(close,open) and Body > Body[1] and GreenCandle and RedCandle[1] //isBearishEngulfing = max(close[1],open[1]) < max(close,open) and min(close[1],open[1]) > min(close,open) and Body > Body[1] and RedCandle and GreenCandle[1] Engulf_curr = 0 - barssince(isBearishEngulfing) + barssince(isBullishEngulfing) Engulf_Buy = Engulf_curr < 0 ? 1 : 0 Engulf_Sell = Engulf_curr > 0 ? 1 : 0 // Price vs MM smma(src, len) => smma = 0.0 smma := na(smma[1]) ? sma(src, len) : (smma[1] * (len - 1) + src) / len smma ma(smoothing, src, length) => if smoothing == "RMA" rma(src, length) else if smoothing == "SMA" sma(src, length) else if smoothing == "EMA" ema(src, length) else if smoothing == "WMA" wma(src, length) else if smoothing == "VWMA" vwma(src, length) else if smoothing == "SMMA" smma(src, length) else if smoothing == "HullMA" wma(2 * wma(src, length / 2) - wma(src, length), round(sqrt(length))) else if smoothing == "LSMA" src else if smoothing == "KMA" xPrice = src xvnoise = abs(xPrice - xPrice[1]) nfastend = 0.666 nslowend = 0.0645 nsignal = abs(xPrice - xPrice[length]) nnoise = sum(xvnoise, length) nefratio = iff(nnoise != 0, nsignal / nnoise, 0) nsmooth = pow(nefratio * (nfastend - nslowend) + nslowend, 2) nAMA = 0.0 nAMA := nz(nAMA[1]) + nsmooth * (xPrice - nz(nAMA[1])) nAMA else if smoothing == "TMA" sma(sma(close, length), length) else if smoothing == "DEMA" 2 * src - ema(src, length) else if smoothing == "TEMA" 3 * (src - ema(src, length)) + ema(ema(src, length), length) else src MA = ma(typeofMA, source_ma, length_ma) plot(MA, color=#006400FF, title="MA breakout", linewidth=3) macrossover = crossover (source_ma, MA) macrossunder = crossunder(source_ma, MA) since_ma_buy = barssince(macrossover) since_ma_sell = barssince(macrossunder) macross_curr = 0 - since_ma_sell + since_ma_buy bullish_MA_cond = macross_curr < 0 ? 1 : 0 bearish_MA_cond = macross_curr > 0 ? 1 : 0 posUp = (Engulf_Buy ? 1 : 0) + (bullish_MA_cond ? 1 : 0) posDn = (Engulf_Sell ? 1 : 0) + (bearish_MA_cond ? 1 : 0) conditionUP = posUp == 2 and posUp[1] < 2 conditionDN = posDn == 2 and posDn[1] < 2 sinceUP = barssince(conditionUP) sinceDN = barssince(conditionDN) // primary-first signal of the trend nUP = crossunder(sinceUP,sinceDN) nDN = crossover(sinceUP,sinceDN) // and the following secondary signals // save of the primary signal sinceNUP = barssince(nUP) sinceNDN = barssince(nDN) buy_trend = sinceNDN > sinceNUP sell_trend = sinceNDN < sinceNUP // engulfing by barcolor(nUP ? color.orange : na, title="Bullish condition") barcolor(nDN ? color.yellow : na, title="Bearish condition") isLong = nUP isShort = nDN long_entry_price = valuewhen(nUP, close, 0) short_entry_price = valuewhen(nDN, close, 0) longClose = close[1] < MA shortClose = close[1] > MA /////////////////////////////////////////////// //* Backtesting Period Selector | Component *// /////////////////////////////////////////////// StartYear = input(2017, "Backtest Start Year",minval=1980) StartMonth = input(1, "Backtest Start Month",minval=1,maxval=12) StartDay = input(1, "Backtest Start Day",minval=1,maxval=31) testPeriodStart = timestamp(StartYear,StartMonth,StartDay,0,0) StopYear = input(2020, "Backtest Stop Year",minval=1980) StopMonth = input(12, "Backtest Stop Month",minval=1,maxval=12) StopDay = input(31, "Backtest Stop Day",minval=1,maxval=31) testPeriodStop = timestamp(StopYear,StopMonth,StopDay,0,0) testPeriod() => true ////////////////////////// //* Profit Component *// ////////////////////////// input_tp_pips = input(600, "Backtest Profit Goal (in USD)",minval=0) input_sl_pips = input(300, "Backtest STOP Goal (in USD)",minval=0) tp = buy_trend? long_entry_price + input_tp_pips : short_entry_price - input_tp_pips sl = buy_trend? long_entry_price - input_sl_pips : short_entry_price + input_sl_pips long_TP_exit = buy_trend and high >= tp short_TP_exit = sell_trend and low <= tp plot(tp, title="TP", style=plot.style_circles, linewidth=3, color=color.blue) plot(sl, title="SL", style=plot.style_circles, linewidth=3, color=color.red) if testPeriod() strategy.entry("Long", 1, when=isLong) strategy.close("Long", when=longClose ) strategy.exit("XL","Long", limit=tp, when=buy_trend, stop=sl) if testPeriod() strategy.entry("Short", 0, when=isShort) strategy.close("Short", when=shortClose ) strategy.exit("XS","Short", when=sell_trend, limit=tp, stop=sl)