La stratégie est une stratégie de tendance simple et automatique à plusieurs têtes basée sur des indicateurs techniques, applicable aux crypto-monnaies telles que Bitcoin et Ethereum, qui vise à capturer les principales tendances à la hausse et à réduire les pertes de frais de traitement causées par des transactions fréquentes.
L’utilisation du MACD pour déterminer la direction de la tendance, le MACD est plus visible lors de la croix à la hausse;
Calculer les EMA de 20 cycles, les SMA de 100 cycles et les SMA de 200 cycles, les EMA et les SMA étant plus élevés à la hausse;
L’EMA est supérieure à la ligne SMA, et la SMA est supérieure à la ligne SMA.
Il est possible d’arrêter la perte de valeur en plaçant un stop loss, et de se retirer de la perte de valeur en cas de rupture du prix.
Lorsque le prix baisse et que l’EMA franchit le SMA, la position est levée.
Cette stratégie combine plusieurs indicateurs pour déterminer la tendance et le moment de l’entrée, et permet de tirer profit en suivant les principales tendances à la hausse.
La combinaison de plusieurs indicateurs permet de filtrer efficacement les signaux erronés tels que les fausses percées.
L’entrée en bourse uniquement lorsque la tendance est claire permet de réduire les transactions inutiles et de réduire la fréquence des transactions.
Les stratégies de stop loss permettent de contrôler efficacement les pertes maximales d’une seule transaction.
Les données de suivi indiquent que les rendements sont meilleurs dans les deux types de crypto-monnaie.
La logique de la stratégie est simple, claire, facile à comprendre et adaptée aux débutants.
Il est évolutif et peut être optimisé avec d’autres indicateurs.
Le risque d’erreur de jugement est considéré comme un facteur de risque majeur.
Le risque systémique n’est pas évité par une simple détention de position.
Un mauvais réglage du point de rupture peut entraîner une rupture excessive;
Les données de détection ne sont pas représentatives de la performance en temps réel, l’efficacité en temps réel est à vérifier;
L’impact sur le disque dur peut varier sans tenir compte des frais de transaction.
Il n’est pas nécessaire de prendre en compte les caractéristiques des différentes variétés, mais il faut les adapter et les optimiser.
tester différentes combinaisons de paramètres et optimiser les paramètres de l’indicateur;
Le système de filtrage des signaux d’entrée est amélioré avec des indicateurs tels que le KDJ.
Optimiser les stratégies de stop loss et introduire des stop loss dynamiques;
La gestion des fonds du compte et la modification de la taille de la position;
Les caractéristiques de la variété et l’ajustement des paramètres
Les résultats de l’étude sont les suivants:
Test des différentes variétés pour trouver la meilleure.
L’idée générale de la stratégie est claire et compréhensible, et l’utilisation de jugements multi-indicateurs peut filtrer efficacement les signaux erronés. Cependant, il est nécessaire d’optimiser davantage les paramètres, le contrôle des risques, etc., puis de les combiner avec la vérification en direct.
/*backtest
start: 2023-09-06 00:00:00
end: 2023-10-06 00:00:00
period: 1h
basePeriod: 15m
exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT"}]
*/
//@version=4
strategy(title="BTC Long strategy", overlay=true, max_bars_back=3000, initial_capital=1000, commission_value=0.075)
//////////// !!!!!!!!!!!!!!!! WORK BEST IN 2 HOURS for BTC, ETH and ETHXBT !!!!!!!!!!!!!!!!!!! /////////////////////
[macdLine, macdSignalLine, macdHist] = macd(close, 12, 26, 7)
//_rsi_len = input(14, title="RSI length")
_rsi_len = 14
NewValue = 0
PreviousValue = 0
leverage = 1
smaPercentageIncrease = 0.0
SMA_PERCENT_INCREASE = 0.0
float atrValue = 0
bool bPositionOpened = false
float stockPositionSize = 0
float volatilityPercentage = 0.0
bool bDisplayArrow = false
bool bEMAIsRising = false
bool bSMAIsRising = false
bool bSMASlowIsRising = false
bool bMACDIsRising = false
bool bMACDHistIsRising = false
bool bMACDSignalIsRising = false
float stopLoss = input (1.5, "StopLoss in %", type=input.float) //StopLoss associated with the order
//positionSize = input (1000, "in $")
float positionSize = 1000
float currentPrice = close
float stopLossPrice = 0
float entryPrice = 0
//-----------------------------------------------------------
// === INPUT BACKTEST RANGE ONE YEAR
//FromDay = input(defval = 01, title = "From Day", minval = 1, maxval = 31)
//FromMonth = input(defval = 01, title = "From Month", minval = 1, maxval = 12)
//FromYear = input(defval = 2020, title = "From Year", minval = 2017)
FromDay = 01
FromMonth = 01
FromYear = 2019
//ToDay = input(defval = 01, title = "To Day", minval = 1, maxval = 31)
//ToMonth = input(defval = 01, title = "To Month", minval = 1, maxval = 12)
//ToYear = input(defval = 2023, title = "To Year", minval = 2017)
ToDay = 31
ToMonth = 12
ToYear = 2099
// === FUNCTION EXAMPLE ===
start = timestamp(FromYear, FromMonth, FromDay, 00, 00) // backtest start window
finish = timestamp(ToYear, ToMonth, ToDay, 23, 59) // backtest finish window
window() => true // create function "within window of time"
//emaLength = input(20, "EMA Length")
//smaLength = input(100, "SMA Length")
//smaSlowLength = input(200, "SMA Length")
emaLength = 20
smaLength = 100
smaSlowLength = 200
ema = ema(close, emaLength)
sma = sma(close, smaLength)
smaSlow = sma(close, smaSlowLength)
plot(sma, color=color.green)
plot(smaSlow, color=color.orange)
plot(ema, color=color.yellow)
//reload previous values
stopLossPrice := na(stopLossPrice[1]) ? 0.0 : stopLossPrice[1]
entryPrice := na(entryPrice[1]) ? 0.0 : entryPrice[1]
bPositionOpened := na(bPositionOpened[1]) ? false : bPositionOpened[1]
positionSize := na(positionSize[1]) ? 50000 : positionSize[1]
stockPositionSize := na(stockPositionSize[1]) ? 0 : stockPositionSize[1]
//leverage := na(leverage[1]) ? 1 : leverage[1]
//ReEvaluate the direction of indicators
bEMAIsRising := rising(ema, 2)
bSMAIsRising := rising(sma, 3)
bMACDIsRising := rising(macdLine, 3)
bMACDHistIsRising := rising(macdHist, 1)
bSMASlowIsRising := rising(smaSlow, 10)
bMACDSignalIsRising := rising(macdSignalLine, 3)
atrValue := atr(14)
volatilityPercentage := (atrValue/currentPrice)*100 //calcute the volatility. Percentage of the actual price
//There is too many signal in tranding market, to avoid this we need to make sure that the smaSlow has a mininal increase
//THIS DOES NOT WORK AT ALL!!!!!
//if bSMASlowIsRising == true
// //calculate the percentegage difference over the last 10 bars
// smaPercentageIncrease := ((smaSlow[0]/sma[10])-1)*100
// if smaPercentageIncrease < SMA_PERCENT_INCREASE
// //Not enough increase we reset the flag
// bSMASlowIsRising := false
if (window())
//Check if we can open a LONG
//sma > smaSlow and
if ( volatilityPercentage < 2 and bPositionOpened == false and bSMASlowIsRising == true and bMACDIsRising == true and bEMAIsRising == true and bSMAIsRising == true and ema[0] > sma[0] and sma[0] < currentPrice)
// add comparaison between macd and macd signal line
//if (bPositionOpened == false and macdSignalLine < macdLine and bMACDIsRising == true and bMACDHistIsRising == true and bEMAIsRising == true and bSMAIsRising == true and ema[1] > sma[1] and sma[1] < currentPrice)
//Enter in short position
stockPositionSize := (positionSize*leverage)/currentPrice //Calculate the position size based on the actual price and the position Size (in $) configured.
//calculate exit values
stopLossPrice := currentPrice*(1-stopLoss/100)
strategy.entry("myPosition", strategy.long, qty=stockPositionSize, comment="BUY at " + tostring(currentPrice))
entryPrice := currentPrice //store the entry price
bPositionOpened := true
bDisplayArrow := true
//if (bPositionOpened == true and (currentPrice <= stopLossPrice or crossunder(ema[1], sma[1]) or currentPrice < sma[1]))
if (bPositionOpened == true and (currentPrice <= stopLossPrice or crossunder(ema[1], sma[1])))
strategy.close("myPosition", comment="" + tostring(currentPrice) ) //Stop
//uncomment the below line to make the bot investing the full portfolio amount to test compounding effect.
//positionSize := positionSize + ((stockPositionSize * currentPrice) - (positionSize*leverage))
//reset some flags
bPositionOpened := false
bDisplayArrow := true
entryPrice := 0.0