移動平均のクロスオーバーに基づくBTC取引戦略

作者: リン・ハーンチャオチャン, 日付: 2023-12-07 14:56:50
タグ:

img

概要

この戦略は,BTCの50日移動平均値と200日移動平均値の黄金十字と死亡十字信号をベースにし,購入・売却信号を生成するための追加の技術指標と組み合わせています.この戦略は,主にBTC/USDTのような明らかなトレンド特性を有する通貨ペアに適しています.

戦略原則

50日間の移動平均が200日間の移動平均を上回って"金十字"を形成すると,BTCが牛市場に入り,購入信号を生成することを示します.50日間の移動平均が200日間の移動平均を下回って"死十字"を形成すると,BTCが熊市場に入り,売却信号を生成することを示します.

この戦略は,基本移動平均の"黄金十字"と"死十字"の信号判断に加えて,以下を含む判断を助けるいくつかの追加の技術指標も含む.

  1. EMAインジケーター: EMAインジケーターを計算して,長さ+オフセットで計算します. 上昇すると,現在の市場は上昇傾向にあることを示します.

  2. 移動平均値とEMAの値関係を比較する.EMA値が50日移動平均値よりも高い場合,購入信号が生成されます.

  3. 価格が前回のKラインの低値と比較して1%以上下がったかどうかを確認します.そうであれば,売り信号を生成します.

上記のいくつかの指標を組み合わせることで,いくつかの間違った信号をフィルタリングし,戦略の取引決定はより信頼性があります.

利点分析

この戦略には以下の利点があります.

  1. 主な取引信号として移動平均を用いることで,市場のノイズをフィルターし,トレンドの方向性を特定することができます.

  2. 複数の補助技術指標と組み合わせることで,信号の信頼性が向上し,偽信号をフィルタリングすることができます.

  3. 適切なストップ・ロスの戦略を採用することで 単一の損失を効果的に制御できます

  4. 比較的単純な取引論理は理解し実行しやすいので,定量取引の初心者にも適しています.

  5. 設定可能なパラメータはたくさんあり,自分の好みに合わせて調整できます.

リスク分析

この戦略には注意すべきリスクもあります.

  1. 移動平均値自体も 遅滞性があり 価格の急速な逆転の機会を逃している可能性があります

  2. 補助指標を追加することで ルール数が増加し 誤った信号が生じる可能性も高まります

  3. 誤ったストップ・ロスの設定により損失が増加する可能性があります.

  4. 不適切なパラメータ設定 (移動平均長等) も戦略結果に影響を与える.

対応する解は:

  1. 移動平均周期を適切に短縮し,パラメータ最適化範囲を拡大する.

  2. バックテストデータ量を増やして信号の質をチェックする

  3. 利得停止を設定する際にストップ・ロスの範囲を適切に緩める.

  4. パラメータの最適化を増やして 最高のパラメータの組み合わせを見つけます

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

この戦略は,次の方向でも最適化できます.

  1. 自動パラメータ最適化を実現するために 機械学習アルゴリズムを増やします

  2. 複数のサブ戦略を構築し,投票メカニズムを通じて決定を行うために,より多くの補助指標を追加します.

  3. 価格突破を特定するために 突破戦略を試してみてください

  4. 価格動向を予測するために ディープラーニングを使います

  5. ストップ・ロスのメカニズムを最適化して ダイナミック・トラッキング・ストップ・ロスを達成する.

上記の最適化は意思決定の正確性を向上させ,戦略の収益性と安定性を高めることができます.

概要

この戦略は,主にBTCの移動平均クロスオーバーに基づいて取引決定を行い,シグナルをフィルタリングするためのEMAなどの技術指標によって支援されます.この戦略は強いトレンドフォロー能力と高い構成可能性を有し,初心者の定量的な取引戦略として適しています.しかし,注意する必要がある特定の遅れのリスクもあります.次の最適化方向は,機械学習,ポートフォリオ戦略,ストップ損失戦略などの複数の次元からすることができます.


/*backtest
start: 2023-11-06 00:00:00
end: 2023-12-06 00:00:00
period: 1d
basePeriod: 1h
exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT"}]
*/

//@version=5
strategy('JayJay BTC Signal', overlay=true, initial_capital=100, currency='USD', default_qty_value=100, default_qty_type=strategy.percent_of_equity, commission_value=0, calc_on_every_tick=true)

securityNoRepaint(sym, tf, src) => request.security(sym, tf, src[barstate.isrealtime ? 1 : 0])[barstate.isrealtime ? 0 : 1]

//200 50 Moving Average
ma50Len = input.int(50, minval=1, title='MA50-Length')
ma50Src = input(close, title='MA50-Source')
ma50Show = input(true, title='Show SMA50 on chart')
ma50Close = ta.sma(ma50Src, ma50Len)
ma50CloseTimeframe = input.timeframe("240", "Ma50 Timeframe", group = "EMA Options")
ma50Open = ta.sma(open, ma50Len)
ma200Len = input.int(200, minval=1, title='MA200-Length')
ma200Src = input(close, title='MA200-Source')
ma200Show = input(true, title='Show SMA200 on chart')
ma200CloseTimeframe = input.timeframe("D", "Ma200 Timeframe", group = "EMA Options")
ma200Close = ta.sma(ma200Src, ma200Len)
ma200Open = ta.sma(open, ma200Len)
//plot(ma200Close, color=color.new(#0b6ce5, 0), title='MA200')
//plot(ma50Close, color=color.new(#00d8ff, 0), title='MA50')

sma50 = securityNoRepaint(syminfo.tickerid, ma50CloseTimeframe, ma50Close)
plot(sma50 and ma50Show ? sma50 : na, color=color.new(#00d8ff, 0), title='SMA50')
sma200 = securityNoRepaint(syminfo.tickerid, ma200CloseTimeframe, ma200Close)
plot(sma200 and ma200Show ? sma200 : na, color=color.new(#00d8ff, 0), title='SMA200')

// Short/Long EMA
// Define the offset value
EMAOffsetValue = input.int(2, title='EMA Offset', minval=0)
emaplot = input(true, title='Show EMA on chart')
len = input.int(20, minval=1, title='ema Length') + EMAOffsetValue
emaCloseTimeframe = input.timeframe("240", "EMA 1 Timeframe", group = "EMA Options")
emaOpen = ta.ema(open, len)
emaClose = ta.ema(close, len)

ema = securityNoRepaint(syminfo.tickerid, emaCloseTimeframe, emaClose)

up = emaClose > ema[1]
down = emaClose < ema[1]
mycolor = up ? color.green : down ? color.red : color.blue

plot(ema and emaplot ? ema : na, title='Signal EMA', color=mycolor, linewidth=3)
//plot(emaClose and emaplot ? emaClose : na, title='Signal 20 EMA', color=color.yellow, linewidth=3)

ma50GreaterThanMa200 = sma50 > sma200

last3BarUp = ema > ema[1]

startLong = up and ema > sma50 and ma50GreaterThanMa200 and (100 - (sma50 / ema * 100) > 1.0)

startFrom = input(timestamp("20 Jan 2000 00:00"), "StartFrom")

yearFilter = true

alertLongPositionMessage = "{\"direction:\": \"long\", \"action\": \"{{strategy.order.action}}\", \"price\": \"{{strategy.order.price}}\", \"qty\": \"{{strategy.position_size}}\", \"symbol\": \"{{ticker}}\", \"date\": \"{{time}}\"}"

if true and startLong and yearFilter
    strategy.entry('Long', strategy.long, comment = "Long", alert_message = alertLongPositionMessage)

longStopLossLevel = open * 0.05
strategy.exit('StopLoss', from_entry='Long',comment = "StopLoss!", loss=longStopLossLevel, profit=close * 0.3, alert_message = alertLongPositionMessage)
longPercentageChange = low / close[1] * 100 - 100
is1PercentLower = longPercentageChange < -0.1
closeLongPositionWhen = (down and is1PercentLower) or (emaClose < sma50)
if closeLongPositionWhen
    strategy.close('Long', comment = "Fuck It!", alert_message =  alertLongPositionMessage)

bgcolor(startLong ? color.green : na, transp=90)



もっと