启动交易模型,并构建 EA
! I8 K; L, V0 e2 G) E在解决系统品质因数之前,有必要创建一个能在测试中使用的基本系统。 我们选择了一个简单的系统:我们先选择一个随机数字,若它是偶数,我们就开仓做多;否则,我们开仓做空,因为数字是奇数。: O0 v! z' x1 A2 |$ Y
为了保持随机抽取,我们调用 MathRand() 函数,它提供一个介于 0(零)至 32767 之间的数字。 此外,为了令系统更加平衡,我们将添加两条互补规则。 有了这三条规则,我们将努力确保系统更加可靠。
7 m1 j! _; j" [4 a) O4 O以下是制定这些规则的代码。. M. g0 D! T" o) x: t% f& h/ M4 B
//--- Indicator ATR(1) with EMA(8) used for the stop level...
, }, |% G) ]3 ~ J+ y2 v* l; _7 R8 Fint ind_atr = iATR(_Symbol, PERIOD_CURRENT, 1);4 k5 m, f M) {# ~9 d b
int ind_ema = iMA(_Symbol, PERIOD_CURRENT, 8, 0, MODE_EMA, ind_atr);
0 T8 q" g: E6 ~. Q( D! e" }//--- Define a variable that indicates that we have a deal...
' [2 N( J* R# ~- [: q4 ]bool tem_tick = false;
2 j: P" ]0 d1 L) @1 G//--- An auxiliary variable for opening a position
1 u' |1 x# U: x0 M. p' a#include<Trade/Trade.mqh>$ P. D1 k P0 Y
#include<Trade/SymbolInfo.mqh>
( K$ T% [7 w) a5 N" ECTrade negocios;1 L# V0 ~- z; w
CSymbolInfo info;
. V, P& R, j) n! R' V//--- Define in OnInit() the use of the timer every second
1 Q( x+ ~) Q- w- l7 ~//--- and start CTrade) ?' ]/ N! I$ `4 E
int OnInit()( W7 X1 P2 I* \" S
{, `5 h" h9 C) K( L3 \
//--- Set the fill type to keep a pending order4 ~2 q5 m7 [2 I
//--- until it is fully filled
, f3 V$ k' c+ O2 M9 }6 Rnegocios.SetTypeFilling(ORDER_FILLING_RETURN);
; b+ T+ n7 B! s. j2 v//--- Leave the fixed deviation at it is not used on B3 exchange$ t/ d, A" T- p4 q4 p9 n- {
negocios.SetDeviationInPoints(5);! f1 d8 f7 u* {. H& V. `
//--- Define the symbol in CSymbolInfo...( \4 B: ~8 }) I0 o0 a
info.Name(_Symbol);( D5 R5 f' u3 f# `9 C( r
//--- Set the timer...& \. Z! g0 X2 c* q5 e
EventSetTimer(1);$ p0 H" A k5 H4 O) W/ Y1 v8 {; ~
//--- Set the base of the random number to have equal tests...
4 }- {) o# B+ Z0 ~, T+ N) q( vMathSrand(0xDEAD);
; c" q- G, ^0 v5 jreturn(INIT_SUCCEEDED);9 b6 D( [2 P' v
}
4 f2 R* V4 H$ F+ B//--- Since we set a timer, we need to destroy it in OnDeInit().$ h0 E( K1 A; u4 u2 v! h: M+ g! I; Q
void OnDeinit(const int reason)9 W' s {% V0 K+ O; b! T
{
9 `: l! T' U- C1 v, tEventKillTimer();, `8 v' G' J: }6 e: I: M6 o
}" J# ?! D3 |, K/ a9 N% Y# C0 }+ _
//--- The OnTick function only informs us that we have a new deal
( t8 g9 t, M5 _6 L: O" {void OnTick()
+ r }- N3 O6 C1 Y{
1 ^. Z3 ]1 q) u' U* o7 Btem_tick = true;: Z" D) C4 K% N& |" b, D5 ^
}
1 c2 U: p' g# B9 c) @! J//+------------------------------------------------------------------+
8 n& a. G" p) X# t4 Z//| Expert Advisor main function |
# P x' e$ l) v) v5 | u//+------------------------------------------------------------------+3 N, l/ i( b& `. t# @1 }
void OnTimer()7 ~( G' e5 V3 a; Y: K, N# g* X* w+ e2 X
{9 U$ `6 h6 N) R+ L
MqlRates cotacao[];
+ G9 m5 s. f1 a, o8 Sreturn ;" h9 T; ~2 F/ `( A# v0 S# y
if (negocios_autorizados == false) // are we outside the trading window?
+ w t; V# S0 \6 ~* E/ ^' Preturn ;
; [1 _* `2 O' V9 R! _& v//--- We are in the trading window, try to open a new position!
( j& E( W$ l: `8 M5 f+ vint sorteio = MathRand();
& O: i1 G8 ~3 j7 R$ N# e//--- Entry rule 1.1
: j* F- n( c! B7 s2 g; @if(sorteio == 0 || sorteio == 32767)! K/ ^, n0 E& ]5 L7 G7 R
return ;
8 J6 b3 ]* C: Zif(MathMod(sorteio, 2) == 0) // Draw rule 1.2 -- even number - Buy
7 ^. H3 B( _% W8 t1 E{
0 R. w7 [8 F1 k1 G( Nnegocios.Buy(info.LotsMin(), _Symbol);) f" \# x1 E+ B
}
; x9 ?: _4 N# u+ {$ F3 }else // Draw rule 1.3 -- odd number - Sell
. W1 k/ j, ^$ h, U+ {{7 r) d: [% ^( |7 R. o+ y4 O
negocios.Sell(info.LotsMin(), _Symbol);- B8 N5 R1 ~3 v$ Z7 p% T2 b
}2 Z" W. K8 F. w9 ?# V0 A4 m/ i; `8 G+ `
}/ W) ^1 j8 I( o0 D
//--- Check if we have a new candlestick...
* r9 c* u0 l% J T6 ]bool tem_vela_nova(const MqlRates &rate)
; y. W K; _$ b- t+ s{ s3 P, n" q$ l
{
$ e7 K* l4 C* t/ C' j4 K4 l. x' `+ Aret = true;
% u4 M' h2 |# b6 ~; n1 g Lclose_positions = false;! D% v& W0 e3 F2 \5 f9 M& r
}- s& j; K% f }4 q! a$ H
else. [2 Q8 I1 V: h: W: s2 ?. o$ O
{) H' r' ^: g# m% {7 i( [
if(mdt.hour == 16)3 Y( |3 j+ O3 @
close_positions = (mdt.min >= 30);
; G u: r0 U; H* |}
6 }3 E4 ~) p8 f' y}' @( [, _% J+ v9 ~- K. n t& X& ^
return ret;7 P/ C, J, V, M' _7 ?$ I
}. W' F" c; w! j5 c' m% e; D- z6 J
//---$ H' f, E/ z' I: G* X% s# f, u) \5 V
bool arruma_stop_em_posicoes(const MqlRates &cotacoes[])
$ \( z/ ^# a9 b, `8 H* d9 v{
5 `- K; V# N; W9 Sif(PositionsTotal()) // Is there a position?
% d0 S9 P$ P2 t{
0 S9 S% O/ v4 M/ s- zdouble offset[1] = { 0 };
3 r, } e! m' ]if(CopyBuffer(ind_ema, 0, 1, 1, offset) == 1 // EMA successfully copied?4 C& u/ v3 R% y/ q3 y; S
&& PositionSelect(_Symbol)) // Select the existing position!
* W0 X$ S1 |3 f: [{
" c1 v& C$ A( J) xENUM_POSITION_TYPE tipo = (ENUM_POSITION_TYPE) PositionGetInteger(POSITION_TYPE);
+ ?0 T1 t/ x v6 R! ^0 @! ]0 A" kdouble SL = PositionGetDouble(POSITION_SL);
7 b& R5 M# j$ adouble TP = info.NormalizePrice(PositionGetDouble(POSITION_TP));) a( |/ f' r4 E' t2 n0 I* o
if(tipo == POSITION_TYPE_BUY)
' ?9 \; J- |# B! H. V- D1 `/ d{$ O$ _& ?. H; p) q& V! p
if (cotacoes[1].high > cotacoes[0].high)
& g# X( P- y: h- H; X0 ^+ j{: M+ [+ i9 L7 Y, ^6 i* V1 \! d% L7 d
double sl = MathMin(cotacoes[0].low, cotacoes[1].low) - offset[0];
! g% e! k" k2 W5 j4 u5 h xinfo.NormalizePrice(sl);1 a) p5 V- P* @9 [, X$ C" q
if (sl > SL)
7 L4 d* @, J. I( S0 }{
* d7 Z0 \/ b# h5 \6 \; ^# c2 inegocios.PositionModify(_Symbol, sl, TP);" {' q4 u% f* M0 Q @4 h
}( [1 ]) K3 ^& B: Y- _- p' X
}
# p$ v- v7 E( y! F7 p}
! w- c5 U5 S* `9 [& E# H7 _else // tipo == POSITION_TYPE_SELL
. u ~4 t. e6 s5 v/ U{
. a1 G" ]8 F. b1 D+ u. sif (cotacoes[1].low < cotacoes[0].low)
2 c* o# v& L6 B& O; F4 X# Y{
, q2 f% Y4 C, Z4 g: ~+ Z7 K a4 Nreturn true;0 E ^1 @3 i/ h
}* F( |* J' o+ X+ Q$ g, P, t
// there was no position1 k; f( F5 H+ K' h
return false;
8 d! G8 q# {4 E7 ]( D5 I* V}& T2 t% `8 W) o3 a6 D7 b
我们简略研究一下上面的代码。 我们将经均化计算的 ATR 值来判定止损步长,即我们发现当前烛条超过前一根时,将止损价位放置在烛条的边界。 这是在函数 arruma_stop_em_posicoes 中完成的。 当其返回 true 时,已有设置,且我们无需在 OnTimer 的主代码中前进。 我使用该函数取代 OnTick,因为我不需要针对每笔执行的交易运行一遍大函数。 函数应该在所定义周期的每根新烛条建立时执行。 在 OnTick 中,设置 true 值表示前一笔交易。 这是必要的;否则,在休市期间,策略测试器将引入暂停,因为即使没有前一笔的交易,它也会执行该函数。+ m8 V+ J5 a: \
到该处为止,一切都严格按照定义好的计划进行,包括两个指定的窗口。 第一个是开仓交易的窗口,在 11:00 到 4:00 之间。 第二个是管理窗口,它允许算法管理持仓,移动其止损价位,直至 16:30 — 此时它应该把当天的所有交易了结。 |