동적 위치 재균형 트렌드 추적 시스템

저자:차오장, 날짜: 2024-01-26 14:41:08
태그:

img

전반적인 설명

이 전략은 지수적인 이동 평균 크로스오버 시스템과 거북이 거래 시스템을 통합합니다. 두 가지 인기있는 체계적인 거래 전략입니다. 그것은 특히 다이얼 타임프레임에 대해 설계되었습니다. 역동적으로 포지션을 관리함으로써 실시간 시장 트렌드를 추적합니다.

전략 논리

이 전략에는 두 가지 하위 전략이 있습니다. 트렌드 전략과 브레이크아웃 전략입니다.

트렌드 전략은 빠른 EMA와 느린 EMA 크로스오버를 거래 신호로 사용합니다. 빠른 EMA 기간은 사용자 정의이며 느린 EMA 기간은 빠른 EMA의 5배입니다. 신호는 EMA 차이를 252 기간 수익 표준 오차로 나누면서 생성됩니다. 이는 더 신뢰할 수있는 신호를 생성하기 위해 변동성에 조정됩니다. 새로운 트렌드 형성을 감지 할 때 길거나 짧습니다.

브레이크아웃 전략은 고정된 뷰백 기간 동안 가장 높은 가격과 가장 낮은 가격의 평균을 기준으로 사용합니다. 가격이 일정 비율로 기준보다 높거나 낮을 때 긴 / 짧은 신호가 생성됩니다.

포지션 사이징은 최근 가격 변동성과 사용자 정의 연간 리스크 타겟을 기반으로 합니다. 변동성이 낮을 때 더 큰 사이즈를 취하고 변동성이 높을 때 더 작은 사이즈를 취합니다. 이것은 리스크 조정과 함께 동적인 포지션 관리를 실현합니다.

하드 스톱은 실제 평균 범위의 배수로 설정됩니다. 트레일링 스톱은 최근 최고 최고 또는 최저 낮은 가격을 추적합니다.

이점 분석

이 전략의 주요 장점은 다음과 같습니다.

  1. 트렌드 추적과 브레이크아웃 하위 전략을 결합하면 강력한 안정성을 가지고 다른 시장 환경에 적응할 수 있습니다.

  2. 고급 포지션 크기와 위험 관리 기술을 적용하면 포지션을 동적으로 관리하고 위험을 효과적으로 제어합니다.

  3. 최근 변동성과 연간 위험 목표에 기초한 변동성 조정 포지션은 높은/저한 변동성 체제에서 상대적으로 안정적인 포트폴리오 위험을 유지합니다.

  4. 실제 가격 변동에 기초한 스톱 로스를 설정하면 스톱 러스에서 불필요한 작은 손실을 피할 수 있습니다.

  5. 트레일링 스톱을 실시간으로 조정하면 유연하게 트렌드를 따라 수익을 기록하고 적시에 멈춥니다.

위험 분석

이 전략의 주요 위험은 다음과 같습니다.

  1. 매개 변수 최적화에 의존합니다. 다른 매개 변수들은 전략 성능에 상당한 영향을 미치므로 최적의 매개 변수를 찾기 위해 포괄적인 테스트가 필요합니다.

  2. 격동적인 트렌드에서 빈번한 스톱 아웃. 스톱 손실 폭이 느려지고 스톱 메커니즘이 최적화 될 수 있습니다.

  3. 초기 자본과 거래 비용에 대한 민감성: 초기 자본의 부족과 높은 거래 비용은 수익성에 부정적인 영향을 미칩니다.

  4. 포지션 크기와 리스크 통제를 위해 정확한 변동성 추정치에 의존하는 것. 불확정한 변동성 추정치로 인해 포지션 크기가 너무 크거나 너무 작습니다.

최적화 방향

주요 최적화 방향은 다음과 같습니다.

  1. 더 큰 역사 데이터 세트를 통해 더 많은 백테스팅을 통해 최적의 매개 변수 세트를 검색하십시오.

  2. 이동 정지, 시간 정지, 변동성 정지 등 다양한 정지를 테스트하여 정지 메커니즘을 개선하십시오.

  3. 가장 좋은 위험 수익 프로파일을 찾기 위해 다른 위험 타겟을 테스트하여 포지션 크기와 위험 관리를 최적화하십시오. 또한 다른 레버리지 레벨의 영향을 테스트하십시오.

  4. 신호 정확성과 전략 안정성을 높이기 위해 더 많은 보조 지표를 시도해보세요.

  5. 위치 할당의 정확성을 향상시키기 위해 더 높은 시간 프레임 신호로 결정을 돕는 다른 보유 기간을 테스트합니다.

결론

이 전략은 트렌드 추종 및 브레이크아웃이라는 두 가지 주요 유형의 거래 전략을 통합합니다. 고급 동적 위치 조정 기술을 적용함으로써 수익으로 시장의 움직임을 추적하는 동안 위험을 효과적으로 제어합니다. 강력한 수익 잠재력을 입증하고 추가 테스트 및 최적화에 가치가 있습니다.


/*backtest
start: 2023-12-01 00:00:00
end: 2023-12-31 23:59:59
period: 1h
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/
// © Crunchster1

//@version=5
strategy(title="Crunchster's Turtle and Trend System", shorttitle="Turtle Trend", overlay=true, slippage=10, pyramiding=1, precision = 4, calc_on_order_fills = false, calc_on_every_tick = false, default_qty_value = 0.1, initial_capital = 1000, commission_value = 0.06, process_orders_on_close = true)

// Inputs and Parameters
src = input(close, 'Source', group='Strategy Settings')
length = input.int(title="Lookback period for fast EMA", defval=10, minval=2, group='Strategy Settings', tooltip='This sets the lookback period for the fast exponential moving average. The slow EMA is 5x the fast EMA length')
blength = input.int(title="Lookback period for Breakout", defval=20, minval=5, step=5, group='Strategy Settings')

long = input(true, 'Long', inline='08', group='Strategy toggle')
short = input(true, 'Short', inline='08', group='Strategy toggle', tooltip='Toggle long/short strategy on/off')

EMAwt = input(false, 'Trend', inline='01', group='Strategy toggle')
breakwt = input(true, 'Breakout', inline='01', group='Strategy toggle', tooltip='Toggle trend/breakout strategy on/off')

stopMultiple = input.float(2, 'Stop multiple', step=0.5, group='Risk Management Settings', tooltip='Multiple for ATR, setting hard stop loss from entry price')
trail = input.int(10, 'Trail lookback', step=5, group='Risk Management Settings', tooltip='Lookback period for the trailing stop')
lev = input.float(1, 'Max Leverage', step=0.5, group='Risk Management Settings', tooltip='Max leverage sets maximum allowable leverage of total capital (initial capital + any net profit), capping maximum volatility adjusted position size')
riskT = input.float(15, maxval=75, title='Annualised Volatility Target %', group='Risk Management Settings', tooltip='Specify annual risk target, used to determine volatility adjusted position size. Annualised daily volatility is referenced to this value and position size adjusted accordingly')
comp = input(true, 'Compounding', inline='09', group='Risk Management Settings')
Comppct = input.float(50, '%', step=5, inline='09', group='Risk Management Settings', tooltip='Toggle compounding of profit, and set % of profit to compound')

// Backtesting period
FromDay = input.int(defval=1, title='From Day', minval=1, maxval=31, inline='04', group='Backtest range')
FromMonth = input.int(defval=1, title='From Mon', minval=1, maxval=12, inline='04', group='Backtest range')
FromYear = input.int(defval=2018, title='From Yr', minval=1900, inline='04', group='Backtest range', tooltip='Set start of backtesting period')
ToDay = input.int(defval=1, title='To Day', minval=1, maxval=31, inline='05', group='Backtest range')
ToMonth = input.int(defval=1, title='To Mon', minval=1, maxval=12, inline='05', group='Backtest range')
ToYear = input.int(defval=9999, title='To Yr', minval=1900, inline='05', group='Backtest range', tooltip='Set end of backtesting period')

start = timestamp(FromYear, FromMonth, FromDay, 00, 00)
finish = timestamp(ToYear, ToMonth, ToDay, 23, 59)
window = time >= start and time <= finish

// Breakout strategy
lower = ta.lowest(low[1], blength)
upper = ta.highest(high[1], blength)
basis = math.avg(upper, lower)
signal = 20*(close - basis) / (upper - lower)

// Trend strategy
fEMA = ta.ema(close[1], length)
sEMA = ta.ema(close[1], length*5)
emadiff = fEMA - sEMA
nemadiff = 5*emadiff/(ta.stdev(close - close[1], 252))

//Risk Management formulae
strategy.initial_capital = 50000
tr = math.max(high - low, math.abs(high - close), math.abs(low - close)) //True range
stopL = ta.sma(tr, 14) //Average true range
stdev = ta.stdev(close-close[1], 14) //volatility of recent returns
maxcapital = strategy.initial_capital+strategy.netprofit //Maximum capital available to invest - initial capital net of profit
annvol = 100*math.sqrt(365)*stdev/close //converts recent volatility of returns into annualised volatility of returns - assumes daily timeframe

risk = 1.1
if comp
    risk := (strategy.initial_capital+(Comppct*strategy.netprofit/100))//adjust investment capital to include compounding
else
    risk := strategy.initial_capital

shares = (risk * (riskT/annvol)) / close //calculates volatility adjusted position size, dependent on user specified annualised risk target
if ((shares*close) > lev*maxcapital) //ensures position size does not exceed available capital multiplied by user specified maximum leverage
    shares := lev*maxcapital/close

//To set the price at the entry point of trade
Posopen() =>
    math.abs(strategy.position_size[1]) <= 0 and math.abs(strategy.position_size) > 0

var float openN = na
if Posopen()
    openN := stopL

// Trailing stop
tlower = ta.lowest(low[1], trail)
tupper = ta.highest(high[1], trail)
tbasis = math.avg(tupper, tlower)
tsignal = 20*(close - tbasis) / (tupper - tlower)

// Strategy Rules
if EMAwt
    if long
        longCondition2 = (nemadiff >2 and nemadiff[1] <2) and window
        exitlong = tsignal <= -10
        if (longCondition2)
            strategy.entry('Trend Long!', strategy.long, qty=shares)
        if strategy.position_size > 0    
            strategy.exit('Stop Long', from_entry = 'Trend Long!', stop=(strategy.opentrades.entry_price(0) - (openN * stopMultiple)))
        if (exitlong)
            strategy.close('Trend Long!', immediately = true)

    if short
        shortCondition2 = (nemadiff <-1 and nemadiff[1] >-1) and window
        exitshort = tsignal >= 10
        if (shortCondition2)
            strategy.entry('Trend Short!', strategy.short, qty=shares)
        if strategy.position_size < 0   
            strategy.exit('Stop Short', from_entry = 'Trend Short!', stop=(strategy.opentrades.entry_price(0) + (openN * stopMultiple)))
        if (exitshort)
            strategy.close('Trend Short!', immediately = true)

if breakwt
    if long
        longCondition1 = (signal >= 10) and window
        exitlong = tsignal <= -10
        if (longCondition1)
            strategy.entry('Break Long!', strategy.long, qty=shares)
        if strategy.position_size > 0    
            strategy.exit('Stop Long', from_entry = 'Break Long!', stop=(strategy.opentrades.entry_price(0) - (openN * stopMultiple)))
        if (exitlong)
            strategy.close('Break Long!', immediately = true)

    if short
        shortCondition1 = (signal <= -10) and window
        exitshort = tsignal >= 10
        if (shortCondition1)
            strategy.entry('Break Short!', strategy.short, qty=shares)
        if strategy.position_size < 0   
            strategy.exit('Stop Short', from_entry = 'Break Short!', stop=(strategy.opentrades.entry_price(0) + (openN * stopMultiple)))
        if (exitshort)
            strategy.close('Break Short!', immediately = true)

// Visuals of trend and direction
plot(nemadiff, title='EMA Forecast', color=color.black, display=display.none)
plot(ta.sma(ta.median(math.sqrt(math.pow(nemadiff,2)), 700), 350), 'Forecast mean', color=color.rgb(245, 0, 0), display=display.none)

MAColor = fEMA > sEMA ? #00ff00 : #ff0000
MA1 = plot(fEMA, title='Fast EMA', color=MAColor)
MA2 = plot(sEMA, title='Slow EMA', color=MAColor)
fill(MA1, MA2, title='Band Filler', color=MAColor)

더 많은