@alavonin

В чём может быть проблема в выставлении стоп-лосса?

//@version=4
strategy('Bollinger Best', overlay=false,
     pyramiding=0,
     calc_on_every_tick=false,
     default_qty_type=strategy.percent_of_equity,
     default_qty_value = 100,
     initial_capital=1000,
     commission_type=strategy.commission.percent,
     commission_value=0.01)

// Параметры Боллинджер Бандс
length = input(20, title='Bollinger Bands Length')
mult = input(2, title='Bollinger Bands Multiplier')

var float obvValue = na
if close > close[1]
    obvValue := na(obvValue[1]) ? volume : obvValue[1] + volume
    obvValue
else if close < close[1]
    obvValue := na(obvValue[1]) ? -volume : obvValue[1] - volume
    obvValue
else
    obvValue := na(obvValue[1]) ? 0 : obvValue[1]
    obvValue

buyLevel = 0
sellLevel = 0


// Параметры MFI
mfiLength = input(14, title='MFI Length')

// Рассчет Боллинджер Бандс
basis = sma(close, length)
dev = mult * stdev(close, length)
upper = basis + dev
lower = basis - dev

// Рассчет MFI
mfi = mfi(close, mfiLength)

entryPercent = 0.7

// Лонг-сигнал при пересечении цены нижней границы Боллинджера, RSI < 50, MFI > 30, ADX < 20 и CCI < -100
longSignal = mfi > 30 and obv > buyLevel and mfi < 40

// Сигнал для открытия шорт-сделки
shortSignal = mfi < 70 and obv < buyLevel and mfi > 60

// Цена для выставления лимитного ордера
limitPriceLong = close * (1 - entryPercent / 100)  // Лимитный ордер на покупку (0.3% ниже текущей цены)
limitPriceShort = close * (1 + entryPercent / 100)  // Лимитный ордер на продажу (0.3% выше текущей цены)

inLong = strategy.position_size > 0
inShort = strategy.position_size < 0
longClose = strategy.position_size < strategy.position_size[1]
shortClose = strategy.position_size > strategy.position_size[1]

// Условие для входа в лонг-сделку через лимитный ордер
longCondition = longSignal

// Условие для входа в шорт-сделку через лимитный ордер
shortCondition = shortSignal

// Лимитный ордер на покупку
if (longCondition)
    strategy.entry("Buy", strategy.long, limit=limitPriceLong)

// Лимитный ордер на продажу
if (shortCondition)
    strategy.entry("Sell", strategy.short, limit=limitPriceShort)

stopPer = input(1.2, title='Stop Loss %') / 100
takePer = input(1.0, title='Take Profit %') / 100
takePer2 = input(1.5, title='Take Profit 2 (%)') / 100

var float longSL = na
var float shortSL = na

longSL := if inLong and barssince(longClose) < barssince(longCondition)
    strategy.position_avg_price
else if inLong
    longSL[1]
else
    close - close * stopPer

shortSL := if inShort and barssince(shortClose) < barssince(shortCondition)
    strategy.position_avg_price
else if inShort
    shortSL[1]
else
    close + close * stopPer

longStop = strategy.position_avg_price * (1 - stopPer)
shortStop = strategy.position_avg_price * (1 + stopPer)
shortTake = strategy.position_avg_price * (1 - takePer)
longTake = strategy.position_avg_price * (1 + takePer)
shortTake2 = strategy.position_avg_price * (1 - takePer2)
longTake2 = strategy.position_avg_price * (1 + takePer2)


if strategy.position_size > 0 
    strategy.exit("TP1/SL", from_entry="Buy", qty_percent = 50, stop=longSL, limit=longTake)
    strategy.exit("TP2/SL", from_entry="Buy", limit=longTake2, stop=longSL)
if strategy.position_size < 0 
    strategy.exit("TP1/SL", from_entry="Sell", qty_percent = 50, stop=shortSL, limit=shortTake)
    strategy.exit("TP2/SL", from_entry="Sell", limit=shortTake2, stop=shortSL)

Есть скрипт стратегии version 4, когда был реализован стоп лосс в безубыток после исполнения первого тейка, стоп лосс начал очень странно выставляться, его фиксированное значение 1% в переменной stopPer, но на стратегии он закрывается в 0.6-08%, хотя если цена не доходит вообще до тейков, он должен закрываться через 1%, в чем может быть ошибка?
  • Вопрос задан
  • 130 просмотров
Пригласить эксперта
Ответы на вопрос 1
@DeskundigeICT
Я думаю, что проблема в выставлении стоп-лосса может быть связана с тем, как вы определяете переменные longSL и shortSL. Вы используете функцию barssince, которая возвращает количество баров с последнего истинного значения условия. Однако, если условие было истинным на текущем баре, то функция вернет ноль, а не единицу. Это может привести к тому, что стоп-лосс будет выставлен на уровне strategy.position_avg_price, а не на уровне close - close * stopPer или close + close * stopPer.

Чтобы исправить эту ошибку, вы можете добавить единицу к результату функции barssince, чтобы учитывать текущий бар. Например, вместо:

longSL := if inLong and barssince(longClose) < barssince(longCondition) strategy.position_avg_price else if inLong longSL1 else close - close * stopPer

Вы можете написать:

longSL := if inLong and barssince(longClose) + 1 < barssince(longCondition) + 1 strategy.position_avg_price else if inLong longSL1 else close - close * stopPer

Аналогично для shortSL. Это должно обеспечить более точное выставление стоп-лосса в соответствии с вашими параметрами.
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы