Стратегия Multi-Time Frame Trend Following DI


Дата создания: 2023-11-07 16:31:07 Последнее изменение: 2023-11-07 16:31:07
Копировать: 0 Количество просмотров: 644
1
Подписаться
1617
Подписчики

Стратегия Multi-Time Frame Trend Following DI

Обзор

Эта стратегия основана на средних трендовых показателях DI+ и DI-, используя показатели DI двух разных временных рамок для определения направления тренда, а затем делая дополнительные пробелы. Когда DI+ более крупного и меньшего временных рамок выше, чем DI-, считается, что тенденция по отношению к пессимизму, делать больше; когда оба временных рама DI-выше, чем DI+, считать, что тенденция к снижению, делать пробелы.

Принципы

Эта стратегия основана на следующих принципах:

  1. Вычислить DI+ и DI- , получив высокую цену, закрытую цену и низкую цену, вычислить DI+ и DI-

  2. Сравнение двух временных рамок DI+ и DI-。 рассчитывается в основном графике (например, 1 час) и в более крупном графике (например, солнечная линия) и сравнивается величина и размер.

  3. Определять направление тренда. Определять как многоголовый тренд, когда ДИ+ более крупного и меньшего временных рамок больше, чем ДИ-; как головной тренд, когда ДИ- обоих временных рамок больше, чем ДИ+.

  4. Выпускает торговый сигнал. Многоголовый сигнал для двух временных рамок DI+>DI-, сделайте больше; пустой головной сигнал для двух временных рамок DI->DI+, сделайте пустой.

  5. Настройка стоп-порога. На основе ATR рассчитывается стоп-порог, реализуется стоп-порог с отслеживанием тренда.

  6. Условия выхода: ликвидация в случае возникновения убытков или обратного движения цены.

Анализ преимуществ

Эта стратегия имеет следующие преимущества:

  1. Используя двойные временные рамки DI, можно отфильтровать некоторые ложные прорывы.

  2. ATR динамически отслеживает остановки, чтобы максимально защитить прибыль и избежать небольших остановок.

  3. Временная остановка может быть контролирована.

  4. Торговля по тренду позволяет постоянно ловить трендовые возможности.

  5. Правила четкие и понятные, удобные для использования в реальном мире.

Риски и решения

Также существуют следующие риски:

  1. Показатель DI задерживается, может пропустить время входа в игру. Параметры могут быть оптимизированы соответствующим образом или в сочетании с другими показателями.

  2. Существуют различные версии о двух временных рамках.

  3. Слишком радикальный стоп-лосс может привести к слишком частому трейдингу.

  4. Частые сделки могут происходить в условиях шока. Можно уменьшить частоту торгов, добавив фильтрующие условия.

  5. Оптимизация параметров зависит от исторических данных, в реальном мире может быть переоптимизация.

Направление оптимизации

Эта стратегия может быть оптимизирована в следующих аспектах:

  1. Оптимизация параметров вычислений DI, поиск оптимальных комбинаций параметров.

  2. Добавление фильтров для других показателей повышает точность сигналов, таких как MACD, KDJ и т. д.

  3. Оптимизация стратегии стоп-порогов, адаптация к более широким рыночным условиям. Можно изменить на мобильные стоп-пороги или стоп-пороги.

  4. Повышение фильтрации транзакций, чтобы избежать важных новостных событий

  5. Тестирование параметров устойчивости различных сортов, повышение адаптивности.

  6. Добавление компонентов машинного обучения, модели обучения суждениям с использованием исторических данных.

Подвести итог

Эта стратегия в целом является типичной стратегией отслеживания тенденций, используя индикаторы DI для определения направления тенденции, установки стоп-лосс для блокировки прибыли и устойчивой прибыли в тренде. Преимущество этой стратегии заключается в четкости стратегии и простоте эксплуатации в реальном мире. В то же время есть некоторые возможности для улучшения, такие как оптимизация параметров, увеличение условий фильтрации и т. Д.

Исходный код стратегии
/*backtest
start: 2022-10-31 00:00:00
end: 2023-11-06 00:00:00
period: 1d
basePeriod: 1h
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/
// © DojiEmoji

//@version=5
strategy("DI+/- multi TF Strat [KL]", overlay=true, pyramiding=1, initial_capital=1000000000, default_qty_type=strategy.percent_of_equity, default_qty_value=5)
var string GROUP_ALERT    = "Alerts"
var string GROUP_SL       = "Stop loss"
var string GROUP_ORDER    = "Order size"
var string GROUP_TP       = "Profit taking"
var string GROUP_HORIZON  = "Time horizon of backtests"
var string GROUP_IND      = "Directional IndicatorDI+ DI-"

// ADX Indicator {
adx_len = input(14, group=GROUP_IND, tooltip="Typically 14")
tf1 = input.timeframe("", title="DI +/- in Timeframe 1", group=GROUP_IND, tooltip="Main: DI+ > DI-")
tf2 = input.timeframe("1D", title="DI +/- in Timeframe 2", group=GROUP_IND, tooltip="Confirmation: DI+ > DI-")
// adx_thres = input(20, group=GROUP_IND)   //threshold not used in this strategy

get_ADX(_high, _close, _low) =>
// (high, close, mid) -> [plus_DM, minus_DM]
    // Based on TradingView user BeikabuOyaji's implementation
    _tr = math.max(math.max(_high - _low, math.abs(_high - nz(_close[1]))), math.abs(_low - nz(_close[1])))
    smooth_tr = 0.0
    smooth_tr := nz(smooth_tr[1]) - nz(smooth_tr[1]) / adx_len + _tr

    smooth_directional_mov_plus = 0.0
    smooth_directional_mov_plus := nz(smooth_directional_mov_plus[1]) - nz(smooth_directional_mov_plus[1]) / adx_len + (_high - nz(_high[1]) > nz(_low[1]) - _low ? math.max(_high - nz(_high[1]), 0) : 0)

    smooth_directional_mov_minus = 0.0
    smooth_directional_mov_minus := nz(smooth_directional_mov_minus[1]) - nz(smooth_directional_mov_minus[1]) / adx_len + (nz(_low[1]) - _low > _high - nz(_high[1]) ? math.max(nz(_low[1]) - _low, 0) : 0)

    plus_DM = smooth_directional_mov_plus / smooth_tr * 100
    minus_DM = smooth_directional_mov_minus / smooth_tr * 100
    // DX = math.abs(plus_DM - minus_DM) / (plus_DM + minus_DM) * 100   // DX not used in this strategy
    [plus_DM, minus_DM]

// DI +/- from timeframes 1 and 2
[plus_DM_tf1, minus_DM_tf1] = get_ADX(request.security(syminfo.tickerid, tf1, high), request.security(syminfo.tickerid, tf1, close),request.security(syminfo.tickerid, tf1, low))
[plus_DM_tf2, minus_DM_tf2] = get_ADX(request.security(syminfo.tickerid, tf2, high),request.security(syminfo.tickerid, tf2, close),request.security(syminfo.tickerid, tf2, low))
// } end of block: ADX Indicator


var string ENUM_LONG      = "LONG"
var string LONG_MSG_ENTER = input.string("Long entered", title="Alert MSG for buying (Long position)", group=GROUP_ALERT)
var string LONG_MSG_EXIT  = input.string("Long closed", title="Alert MSG for closing (Long position)", group=GROUP_ALERT)
backtest_timeframe_start = input(defval=timestamp("01 Apr 2020 13:30 +0000"), title="Backtest Start Time", group=GROUP_HORIZON)
within_timeframe         = true

// Signals for entry
_uptrend_confirmed = plus_DM_tf1 > minus_DM_tf1 and plus_DM_tf2 > minus_DM_tf2
entry_signal_long = _uptrend_confirmed

plotshape(_uptrend_confirmed, style=shape.triangleup, location=location.bottom, color=color.green)
plotshape(not _uptrend_confirmed, style=shape.triangledown, location=location.bottom, color=color.red)

// Trailing stop loss ("TSL") {
tsl_multi                 = input.float(2.0, title="ATR Multiplier for trailing stoploss", group=GROUP_SL)
SL_buffer                 = ta.atr(input.int(14, title="Length of ATR for trailing stoploss", group=GROUP_SL)) * tsl_multi
TSL_source_long           = low
var stop_loss_price_long  = float(0)
var pos_opened_long       = false

stop_loss_price_long := pos_opened_long ? math.max(stop_loss_price_long, TSL_source_long - SL_buffer) : TSL_source_long - SL_buffer

// MAIN: {
if pos_opened_long and TSL_source_long <= stop_loss_price_long
    pos_opened_long := false
    alert(LONG_MSG_EXIT, alert.freq_once_per_bar)
    strategy.close(ENUM_LONG, comment=close < strategy.position_avg_price ? "stop loss" : "take profit")

// (2) Update the stoploss to latest trailing amt.
if pos_opened_long
    strategy.exit(ENUM_LONG, stop=stop_loss_price_long, comment="SL")

// (3) INITIAL ENTRY:
if within_timeframe and entry_signal_long
    pos_opened_long := true
    alert(LONG_MSG_ENTER, alert.freq_once_per_bar)
    strategy.entry(ENUM_LONG, strategy.long, comment="long")

// Plotting: 
TSL_transp_long = pos_opened_long and within_timeframe ? 0 : 100
plot(stop_loss_price_long, color=color.new(color.green, TSL_transp_long))

// CLEAN UP: Setting variables back to default values once no longer in use
if ta.change(strategy.position_size) and strategy.position_size == 0
    pos_opened_long := false

if not pos_opened_long
    stop_loss_price_long := float(0)

// } end of MAIN block