Conversión del asesor experto original MQL4 "RndTrade" en una estrategia StockSharp de alto nivel que realiza entradas de mercado totalmente aleatorias y las sale después de un período de tenencia fijo.
Lógica principal
Suscríbase al tipo de vela configurado (velas de 1 minuto por defecto) y espere a que se completen las barras.
Siempre que la estrategia sea plana, genere un número aleatorio. Un valor superior a 0,5 desencadena una compra en el mercado; de lo contrario, una venta en el mercado, ambos utilizando el volumen comercial configurado.
Registre el tiempo de vela de la entrada y mantenga la posición abierta durante el tiempo de tenencia seleccionado (cuatro horas por defecto).
Una vez transcurrido el cronómetro de retención, cierre toda la posición con la orden de mercado correspondiente.
Parámetros
Nombre
Descripción
Predeterminado
CandleType
Tipo de datos de velas que activan la lógica de decisión aleatoria.
velas de 1 minuto
TradeVolume
Volumen utilizado para cada orden de mercado aleatoria.
1
HoldDuration
Lapso de tiempo para mantener activa cualquier posición aleatoria abierta antes de cerrarla.
4 horas
Notas adicionales
El generador aleatorio se reinicia automáticamente cuando la estrategia comienza a imitar el comportamiento MQL4 de usar la hora local como semilla.
Sólo se utilizan órdenes de mercado, lo que refleja el asesor experto original que ejecutó inmediatamente operaciones sin órdenes pendientes.
No se requieren indicadores adicionales ni reservas históricas; la estrategia sólo se basa en las marcas de tiempo de las velas entrantes y el temporizador interno.
using System;
using StockSharp.Algo.Indicators;
using StockSharp.Algo.Strategies;
using StockSharp.BusinessEntities;
using StockSharp.Messages;
namespace StockSharp.Samples.Strategies;
public class RndTradeRandomHoldStrategy : Strategy
{
private readonly StrategyParam<int> _emaPeriod;
private readonly StrategyParam<int> _momentumPeriod;
private readonly StrategyParam<DataType> _candleType;
private decimal _prevMom; private bool _hasPrev;
private int _cooldown;
public int EmaPeriod { get => _emaPeriod.Value; set => _emaPeriod.Value = value; }
public int MomentumPeriod { get => _momentumPeriod.Value; set => _momentumPeriod.Value = value; }
public DataType CandleType { get => _candleType.Value; set => _candleType.Value = value; }
public RndTradeRandomHoldStrategy()
{
_emaPeriod = Param(nameof(EmaPeriod), 14).SetDisplay("EMA Period", "EMA filter", "Indicators");
_momentumPeriod = Param(nameof(MomentumPeriod), 10).SetDisplay("Momentum", "Momentum period", "Indicators");
_candleType = Param(nameof(CandleType), TimeSpan.FromMinutes(15).TimeFrame()).SetDisplay("Candle Type", "Candle timeframe", "General");
}
/// <inheritdoc />
protected override void OnReseted()
{
base.OnReseted();
_prevMom = default;
_hasPrev = default;
_cooldown = default;
}
/// <inheritdoc />
protected override void OnStarted2(DateTime time)
{
base.OnStarted2(time);
_hasPrev = false;
var ema = new ExponentialMovingAverage { Length = EmaPeriod };
var mom = new Momentum { Length = MomentumPeriod };
var subscription = SubscribeCandles(CandleType);
subscription.Bind(ema, mom, ProcessCandle).Start();
}
private void ProcessCandle(ICandleMessage candle, decimal ema, decimal mom)
{
if (candle.State != CandleStates.Finished) return;
if (!IsFormedAndOnlineAndAllowTrading()) return;
var close = candle.ClosePrice;
if (!_hasPrev) { _prevMom = mom; _hasPrev = true; return; }
if (_cooldown > 0)
{
_cooldown--;
_prevMom = mom;
return;
}
if (close > ema && _prevMom <= 0 && mom > 0 && Position <= 0)
{
var volume = Volume + Math.Abs(Position);
BuyMarket(volume);
_cooldown = 2;
}
else if (close < ema && _prevMom >= 0 && mom < 0 && Position >= 0)
{
var volume = Volume + Math.Abs(Position);
SellMarket(volume);
_cooldown = 2;
}
_prevMom = mom;
}
}
import clr
clr.AddReference("StockSharp.Messages")
clr.AddReference("StockSharp.Algo")
clr.AddReference("StockSharp.Algo.Indicators")
clr.AddReference("StockSharp.Algo.Strategies")
from System import TimeSpan, Math
from StockSharp.Messages import DataType, CandleStates
from StockSharp.Algo.Indicators import ExponentialMovingAverage, Momentum
from StockSharp.Algo.Strategies import Strategy
from datatype_extensions import *
from indicator_extensions import *
class rnd_trade_random_hold_strategy(Strategy):
def __init__(self):
super(rnd_trade_random_hold_strategy, self).__init__()
self._ema_period = self.Param("EmaPeriod", 14).SetDisplay("EMA Period", "EMA filter", "Indicators")
self._momentum_period = self.Param("MomentumPeriod", 10).SetDisplay("Momentum", "Momentum period", "Indicators")
self._candle_type = self.Param("CandleType", DataType.TimeFrame(TimeSpan.FromMinutes(15))).SetDisplay("Candle Type", "Candle timeframe", "General")
@property
def CandleType(self): return self._candle_type.Value
@CandleType.setter
def CandleType(self, value): self._candle_type.Value = value
def OnReseted(self):
super(rnd_trade_random_hold_strategy, self).OnReseted()
self._prev_mom = 0
self._has_prev = False
self._cooldown = 0
def OnStarted2(self, time):
super(rnd_trade_random_hold_strategy, self).OnStarted2(time)
self._prev_mom = 0
self._has_prev = False
self._cooldown = 0
ema = ExponentialMovingAverage()
ema.Length = self._ema_period.Value
mom = Momentum()
mom.Length = self._momentum_period.Value
sub = self.SubscribeCandles(self.CandleType)
sub.Bind(ema, mom, self.OnProcess).Start()
def OnProcess(self, candle, ema_val, mom_val):
if candle.State != CandleStates.Finished:
return
if not self.IsFormedAndOnlineAndAllowTrading():
return
close = candle.ClosePrice
if not self._has_prev:
self._prev_mom = mom_val
self._has_prev = True
return
if self._cooldown > 0:
self._cooldown -= 1
self._prev_mom = mom_val
return
if close > ema_val and self._prev_mom <= 0 and mom_val > 0 and self.Position <= 0:
volume = self.Volume + abs(self.Position)
self.BuyMarket(volume)
self._cooldown = 2
elif close < ema_val and self._prev_mom >= 0 and mom_val < 0 and self.Position >= 0:
volume = self.Volume + abs(self.Position)
self.SellMarket(volume)
self._cooldown = 2
self._prev_mom = mom_val
def CreateClone(self):
return rnd_trade_random_hold_strategy()