0bps

Strategy vault / Mean reversion

Dual Moving Average Reversal Strategy 431003

This strategy uses 2 indicators to generate trading signals: 2/20 Exponential Moving Average and Average True Range Reversal. It combines the ideas of trend following and short-term reversal, aiming to capture…

Author
ChaoZhang
Complexity
Intermediate · 77 lines
Parameters
7
Backtest bar
1d · swing
Tested on
BTC/USDT · futures

IMG

Overview

This strategy uses 2 indicators to generate trading signals: 2/20 Exponential Moving Average and Average True Range Reversal. It combines the ideas of trend following and short-term reversal, aiming to capture reversal opportunities.

Principle

The strategy consists of 2 parts:

  1. 2/20 Exponential Moving Average. It calculates 20-day EMA and generates signals when price crosses EMA up or down.

  2. Average True Range Reversal Indicator. It calculates stop loss level based on ATR, and generates signals when price breaks through the stop loss level. Here 3.5 x ATR is used as the stop level.

The strategy combines the signals from both. It goes short when 2/20 EMA gives long signal while ATR reversal gives short signal. It goes long when opposite signals generated.

Advantage Analysis

The strategy combines trend following and reversal ideas, aiming to capture reversals. The advantages are:

  1. 2/20 EMA identifies mid-term trend, avoids market noise.

  2. ATR reversal captures short-term reversals and opportunities.

  3. Combining the signals captures trend reversal ahead of time and improves profitability.

  4. Reasonable ATR stop loss provides certain risk control.

  5. Customizable ATR multiplier adapts to different products.

  6. Reversal option adapts to different market environments.

Risk Analysis

The risks are:

  1. 2/20 EMA is slow and may miss short-term chances.

  2. ATR stop loss may be penetrated easily. Wider stop loss is needed.

  3. Single indicator signal is unreliable. More filters are needed.

  4. Beware of over-trading.

  5. Parameter tuning and backtest are needed to fit the product.

  6. Strict capital management is needed to control risk per trade.

Optimization Directions

The strategy can be improved from:

  1. Tuning EMA parameters for best combination.

  2. Optimizing ATR multiplier for better stop loss.

  3. Adding filter conditions like volume and volatility.

  4. Adding capital management model for dynamic position sizing.

  5. Adding other stop loss strategies like Chandelier Exit.

  6. Testing parameters across different products.

  7. Adding machine learning models for better performance.

  8. Combining multiple sub-strategies for more Alpha.

Conclusion

The strategy combines two major ideas and has certain advantage of capturing reversals. But inappropriate parameter selection can also introduce risks. Further improvements on stop loss strategy and adding filters can enhance stability and profitability.

Parameters

NameDefaultWhat it controls
v_input_int_114(?●═════ 2/20 EMA ═════●)Length
v_input_int_25(?●═════ Average True Range Reversed ═════●)nATRPeriod
v_input_float_13.5nATRMultip
v_input_bool_1false(?●═════ MISC ═════●)Trade reverse
v_input_int_3true(?●═════ Time Start ═════●)From Day
v_input_int_4trueFrom Month
v_input_int_52005From Year

Source Pine Script

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

//@version=5
////////////////////////////////////////////////////////////
//  Copyright by HPotter v1.0 05/04/2022
// This is combo strategies for get a cumulative signal. 
//
// First strategy
// This indicator plots 2/20 exponential moving average. For the Mov 
// Avg X 2/20 Indicator, the EMA bar will be painted when the Alert criteria is met.
//
// Second strategy
// Average True Range Trailing Stops Strategy, by Sylvain Vervoort 
// The related article is copyrighted material from Stocks & Commodities Jun 2009 
// Please, use it only for learning or paper trading. Do not for real trading.
//
//
// WARNING:
// - For purpose educate only
// - This script to change bars colors.
////////////////////////////////////////////////////////////
EMA20(Length) =>
    pos = 0.0
    xPrice = close
    xXA = ta.ema(xPrice, Length)
    nHH = math.max(high, high[1])
    nLL = math.min(low, low[1])
    nXS = nLL > xXA or nHH < xXA ? nLL : nHH
    iff_1 = nXS < close[1] ? 1 : nz(pos[1], 0)
    pos := nXS > close[1] ? -1 : iff_1
    pos


ATRR(nATRPeriod,nATRMultip) =>
    pos = 0.0
    xATR = ta.atr(nATRPeriod)
    nLoss = nATRMultip * xATR
    xATRTrailingStop = 0.0
    xATRTrailingStop := close > nz(xATRTrailingStop[1], 0) and close[1] > nz(xATRTrailingStop[1], 0) ? math.max(nz(xATRTrailingStop[1]), close - nLoss) :
                          close < nz(xATRTrailingStop[1], 0) and close[1] < nz(xATRTrailingStop[1], 0) ? math.min(nz(xATRTrailingStop[1]), close + nLoss) : 
                          close > nz(xATRTrailingStop[1], 0) ? close - nLoss : close + nLoss
    pos:= close[1] < nz(xATRTrailingStop[1], 0) and close > nz(xATRTrailingStop[1], 0) ? 1 :
    	     close[1] > nz(xATRTrailingStop[1], 0) and close < nz(xATRTrailingStop[1], 0) ? -1 : nz(pos[1], 0) 
    pos

strategy(title='Combo 2/20 EMA & Average True Range Reversed', shorttitle='Combo', overlay=true)
var I1 = '●═════ 2/20 EMA ═════●'
Length = input.int(14, minval=1, group=I1)
var I2 = '●═════ Average True Range Reversed  ═════●'
nATRPeriod = input.int(5, group=I2)
nATRMultip = input.float(3.5, group=I2)
var misc = '●═════ MISC ═════●'
reverse = input.bool(false, title='Trade reverse', group=misc)
var timePeriodHeader = '●═════ Time Start ═════●'
d = input.int(1, title='From Day', minval=1, maxval=31, group=timePeriodHeader)
m = input.int(1, title='From Month', minval=1, maxval=12, group=timePeriodHeader)
y = input.int(2005, title='From Year', minval=0, group=timePeriodHeader)
StartTrade = time > timestamp(y, m, d, 00, 00) ? true : false
posEMA20 = EMA20(Length)
prePosATRR = ATRR(nATRPeriod,nATRMultip)
iff_1 = posEMA20 == -1 and prePosATRR == -1 and StartTrade ? -1 : 0
pos = posEMA20 == 1 and prePosATRR == 1 and StartTrade ? 1 : iff_1
iff_2 = reverse and pos == -1 ? 1 : pos
possig = reverse and pos == 1 ? -1 : iff_2
if possig == 1
    strategy.entry('Long', strategy.long)
if possig == -1
    strategy.entry('Short', strategy.short)
if possig == 0
    strategy.close_all()
barcolor(possig == -1 ? #b50404 : possig == 1 ? #079605 : #0536b3)

Published by ChaoZhang on the FMZ strategy square · last modified 2023-11-03. Collected in the Quant Trading Vault. Unvalidated research: re-test with your own data and costs before trusting it.

Build this with AgenKit

A spec is not a trading system. Paste this into your coding agent and AgenKit runs a specialist team — architecture, test-first build, risk gates, review — with paper trading on by default.

in Claude Code, Cursor, Codex & 4 more
/agenkit build a production-grade trading bot with a backtest engine, risk controls and paper trading by default from strategies/Dual-Moving-Average-Reversal-Strategy-431003.md
  1. npx agenkit install engineering-kit in your project
  2. Paste the command into your agent and approve each phase
  3. Get tests, backtest, risk controls and a paper-trading switch

Understand it first

Before you run this, read the lesson behind the idea and how to backtest it honestly. Specs like this one are the survivors of an unknown number of trials; deflate their results accordingly.

Related specs

esc

Try , , or .

↑↓ move↵ open