English Русский 中文 Español Deutsch 日本語 Português 한국어 Italiano Türkçe
Faites la Promotion de vos Projets de Développement à l'Aide des Bibliothèques EX5

Faites la Promotion de vos Projets de Développement à l'Aide des Bibliothèques EX5

MetaTrader 5Exemples | 12 janvier 2022, 15:06
183 0
---
---

Introduction

Une lecteur sophistiqué n’a pas besoin d’expliquer le but derrière la dissimulation de la fonction et des implémentations de classe dans les bibliothèques. Ceux d'entre vous qui recherchent activement de nouvelles idées voudront peut-être savoir que le fait de cacher les détails d'implémentation des classes/fonctions dans un fichier .ex5 vous permettra de partager vos algorithmes de savoir-faire avec d'autres développeurs, de mettre en place des projets communs et de promouvoir eux dans le Web.

Et tandis que l'équipe MetaQuotes ne ménage aucun effort pour amener la possibilité d'héritage direct des classes de la bibliothèque ex5, nous allons l'implémenter dès maintenant.

Table des matières

1. Exportation et Importation de Fonctions
2. Exportation de l'Implémentation Cachée d'une Classe
3. Initialisation des Variables dans le Fichier .ex5
4. Héritage des Classes d'Exportation
5. Édition des bibliothèques ex5


1. Exportation et Importation de Fonctions

Il s'agit d'une méthode de base sous-jacente à l'exportation de classes. Il y a trois éléments clés qui doivent être pris en compte pour que vos fonctions soient disponibles pour d'autres programmes :

  1. Le fichier à créer doit avoir l'extension .mq5 (pas .mqh) afin d'être compilé en fichier .ex5 ;
  2. Le fichier devra comporter l’instruction du préprocesseur #property library
  3. Le mot clé "export" doit être placé après les en-têtes des fonctions exportées requises
Example 1. Let us create a function to be used in other programs

//--- library.mq5
#property library
int libfunc (int a, int b) export
{
  int c=a+b;
  Print("a+b="+string(с));
  return(с);
}

Après avoir compilé le fichier, vous obtiendrez le fichierlibrary.ex5 depuis duquel libfuncpeut être utilisé dans un autre programme.

Le processus d'importation des fonctions est également très simple. Il est réalisé à l’aide de l’instruction préprocesseur#import .

Example 2. We will use the export function libfunc() in our script

//--- uses.mq5
#import "library.ex5"
  int libfunc(int a, int b);
#import

void OnStart()
{
  libfunc(1, 2);
}

Gardez à l’esprit que la compilateur cherchera les fichiers .ex5 and le dossierMQL5\Libraries Donc si le library.ex5 ne se trouve pas dans ce dossier, vous devrez indiquer le nom du chemin relatif.

Par exemple:

#import "..\Include\MyLib\library.ex5" // the file is located in the MQL5\Include\MyLib folder
#import "..\Experts\library.ex5" // the file is located in the MQL5\Experts\ folder

Pour votre utilisation future, les fonctions peuvent être importées non seulement dans le fichier cible .mq5 mais également dans les fichiers .mqh.

Afin d'illustrer l'application pratique, utilisons quelques graphiques.

Nous allons créer une bibliothèque de fonctions pour l'export. Ces fonctions afficheront des objets graphiques tels que Button, Edit, Label et Rectangle Label sur un graphique, supprimeront les objets du graphique et réinitialiseront les paramètres de couleur du graphique.

Ceci peut être schématisé comme suit :

Schéma d’export de la méthode classe

Le fichier en entier Graph.mq5 peut être disponible à la fin de l’article. Ici, nous ne donnerons qu'un exemple de modèle de la fonction de dessin Modifier.

//+------------------------------------------------------------------+
//| SetEdit                                                          |
//+------------------------------------------------------------------+
void SetEdit(long achart,string name,int wnd,string text,color txtclr,color bgclr,color brdclr,
             int x,int y,int dx,int dy,int corn=0,int fontsize=8,string font="Tahoma",bool ro=false) export
  {
   ObjectCreate(achart,name,OBJ_EDIT,wnd,0,0);
   ObjectSetInteger(achart,name,OBJPROP_CORNER,corn);
   ObjectSetString(achart,name,OBJPROP_TEXT,text);
   ObjectSetInteger(achart,name,OBJPROP_COLOR,txtclr);
   ObjectSetInteger(achart,name,OBJPROP_BGCOLOR,bgclr);
   ObjectSetInteger(achart,name,OBJPROP_BORDER_COLOR,brdclr);
   ObjectSetInteger(achart,name,OBJPROP_FONTSIZE,fontsize);
   ObjectSetString(achart,name,OBJPROP_FONT,font);
   ObjectSetInteger(achart,name,OBJPROP_XDISTANCE,x);
   ObjectSetInteger(achart,name,OBJPROP_YDISTANCE,y);
   ObjectSetInteger(achart,name,OBJPROP_XSIZE,dx);
   ObjectSetInteger(achart,name,OBJPROP_YSIZE,dy);
   ObjectSetInteger(achart,name,OBJPROP_SELECTABLE,false);
   ObjectSetInteger(achart,name,OBJPROP_READONLY,ro);
   ObjectSetInteger(achart,name,OBJPROP_BORDER_TYPE,0);
   ObjectSetString(achart,name,OBJPROP_TOOLTIP,"");
  }

L'import des fonctions requises et leur utilisation seront implémentés dans le fichier cible Spiro.mq5 :

Example 3. Using imported functions

//--- Spiro.mq5 – the target file of the Expert Advisor

//--- importing some graphics functions
#import "Graph.ex5" 
  void SetLabel(long achart, string name, int wnd, string text, color clr, 
               int x, int y, int corn=0, int fontsize=8, string font="Tahoma");
  void SetEdit(long achart, string name, int wnd, string text, color txtclr, color bgclr, color brdclr, 
                 int x, int y, int dx, int dy, int corn=0, int fontsize=8, string font="Tahoma", bool ro=false);
  void SetButton(long achart, string name, int wnd, string text, color txtclr, color bgclr, 
                int x, int y, int dx, int dy, int corn=0, int fontsize=8, string font="Tahoma", bool state=false);
  void HideChart(long achart, color BackClr);
#import

//--- prefix for chart objects
string sID; 
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+

void OnInit()
{
  HideChart(0, clrWhite);
  sID="spiro.";
  DrawParam();
}
//+------------------------------------------------------------------+
//| DrawParam                                                        |
//+------------------------------------------------------------------+
void DrawParam()
{
  color bgclr=clrWhite, clr=clrBlack;
//--- bigger radius    
  SetLabel(0, sID+"stR.", 0, "R", clr, 10, 10+3);
  SetEdit(0, sID+"R.", 0, "100", clr, bgclr, clr, 40, 10, 50, 20);
//--- smaller radius   
  SetLabel(0, sID+"str.", 0, "r", clr, 10, 35+3);
  SetEdit(0, sID+"r.", 0, "30", clr, bgclr, clr, 40, 35, 50, 20);
//--- distance to the center
  SetLabel(0, sID+"stD.", 0, "D", clr, 10, 60+3);
  SetEdit(0, sID+"D.", 0, "40", clr, bgclr, clr, 40, 60, 50, 20);
//--- drawing accuracy
  SetLabel(0, sID+"stA.", 0, "Alfa", clr, 10, 85+3); 
  SetEdit(0, sID+"A.", 0, "0.04", clr, bgclr, clr, 40, 85, 50, 20);
//--- drawing accuracy
  SetLabel(0, sID+"stN.", 0, "Rotor", clr, 10, 110+3); 
  SetEdit(0, sID+"N.", 0, "10", clr, bgclr, clr, 40, 110, 50, 20);
//--- draw button
  SetButton(0, sID+"draw.", 0, "DRAW", bgclr, clr, 39, 135, 51, 20); 
}

Après l'exécution de l'Expert Advisor, les objets apparaîtront sur le graphique :

Exemple d’utilisation d’objets de bibliothèque

Comme nous pouvons le constater,le processus d’exportation des fonctions est pas du tout difficile mais assurez-vous de lire sur certaines restrictions dans l’Aide: export, import


2. Export de l'Implémentation Cachée d'une Classe

Vu que les classes en MQL5 ne peuvent pas encore être directement exportées, nous devrons recourir à une méthode un peu sophistiquée. Elle est axée sur le polymorphisme et fonctions virtuelles. En fait, ce n'est pas la classe elle-même qui est renvoyée par le module ex5 mais un objet créé de celle-ci. Appelons-le Objet caché de l’implémentation.

L'essence de la méthode est de diviser la classe requise en deux afin que la déclaration des fonctions et des variables soit ouverte au public et que les détails de leur implémentation soient cachés dans un fichier .ex5 fermé.

Cela peut être simplement illustré comme ci-dessous. Il existe une classe CSpiro que nous souhaiterions partager avec les autres développeurs sans divulguer les détails de l’implémentation. Admettons qu'il comporte des variables, un constructeur, un destructeur et des fonctions de travail.

Pour exporter la classe, nous allons procéder comme suit :

  • Créez un clone du descendant de la classe CSpiro Appelons-le ISpiro (la première lettre C est remplacée par I comme dérivée du mot "interface")
  • Laissez toutes les variables et les fonctions factices dans la classe initialeCSpiro.
  • Les détails de l’implémentation de la fonction constituerons une nouvelle forme de classe ISpiro class.
  • Ajoutez-en la fonction export qui créera une instance fermée ISpiro.
  • Note! Toutes les fonctions requises disposeront du préfixe virtuel

En conséquence, nous avons deux fichiers :

Example 4. Hiding of the class implementation in the ex5 module

//--- Spiro.mqh – public file, the so called header file

//+------------------------------------------------------------------+
//| Class CSpiro                                                     |
//| Spirograph draw class                                       |
//+------------------------------------------------------------------+
class CSpiro
  {
public:
   //--- prefix of the chart objects
   string            m_sID;
   //--- offset of the chart center
   int               m_x0,m_y0;
   //--- color of the line
   color             m_clr;
   //--- chart parameters
   double            m_R,m_r,m_D,m_dAlfa,m_nRotate;

public:
   //--- constructor
                     CSpiro() { };
   //--- destructor
                    ~CSpiro() { };
   virtual void Init(int ax0,int ay0,color aclr,string asID) { };
   virtual void SetData(double aR,double ar,double aD,double adAlpha,double anRotate) { };

public:
   virtual void DrawSpiro() { };
   virtual void SetPoint(int x,int y) { };
  };

Veuillez noter que toutes les classe fonction sont déclarées avec le mot clé virtual.

//--- ISpiro.mq5 – hidden implementation file

#include "Spiro.mqh"

//--- importing some functions
#import "..\Experts\Spiro\Graph.ex5"
void SetPoint(long achart,string name,int awnd,int ax,int ay,color aclr);
void ObjectsDeleteAll2(long achart=0,int wnd=-1,int type=-1,string pref="",string excl="");
#import

CSpiro *iSpiro() export { return(new ISpiro); }
//+------------------------------------------------------------------+
//| Сlass ISpiro                                                     |
//| Spirograph draw class                                       |
//+------------------------------------------------------------------+
class ISpiro : public CSpiro
  {
public:
                     ISpiro() { m_x0=0; m_y0=0; };
                    ~ISpiro() { ObjectsDeleteAll(0,0,-1); };
   virtual void      Init(int ax0,int ay0,color aclr,string asID);
   virtual void      SetData(double aR,double ar,double aD,double adAlpha,double anRotate);

public:
   virtual void      DrawSpiro();
   virtual void      SetPoint(int x,int y);
  };
//+------------------------------------------------------------------+
//| Init                                                             |
//+------------------------------------------------------------------+
void ISpiro::Init(int ax0,int ay0,color aclr,string asID)
  {
   m_x0=ax0;
   m_y0=ay0;
   m_clr=aclr;
   m_sID=asID;
   m_R=0; 
   m_r=0; 
   m_D=0;
  }
//+------------------------------------------------------------------+
//| SetData                                                          |
//+------------------------------------------------------------------+
void ISpiro::SetData(double aR,double ar,double aD,double adAlpha,double anRotate)
  {
   m_R=aR; m_r=ar; m_D=aD; m_dAlfa=adAlpha; m_nRotate=anRotate;
  }
//+------------------------------------------------------------------+
//| DrawSpiro                                                        |
//+------------------------------------------------------------------+
void ISpiro::DrawSpiro()
  {
   if(m_r<=0) { Print("Error! r==0"); return; }
   if(m_D<=0) { Print("Error! D==0"); return; }
   if(m_dAlfa==0) { Print("Error! Alpha==0"); return; }
   ObjectsDeleteAll2(0,0,-1,m_sID+"pnt.");
   int n=0; double a=0;
   while(a<m_nRotate*2*3.1415926)
     {
      double x=(m_R-m_r)*MathCos(a)+m_D*MathCos((m_R-m_r)/m_r*a);
      double y=(m_R-m_r)*MathSin(a)-m_D*MathSin((m_R-m_r)/m_r*a);
      SetPoint(int(m_x0+x),int(m_y0+y));
      a+=m_dAlfa;
     }
   ChartRedraw(0);
  }
//+------------------------------------------------------------------+
//| SetPoint                                                         |
//+------------------------------------------------------------------+
void ISpiro::SetPoint(int x,int y)
  {
   Graph::SetPoint(0,m_sID+"pnt."+string(x)+"."+string(y),0,x,y,m_clr);
  }
//+------------------------------------------------------------------+

Comme nous pouvons le constater ,la classe cachée a été implémentée dans le fichier.mq5 et comporte la commande préprocesseur #property library. Ainsi, toutes les règles exposées dans la section précédente ont été respectées.

Notez également que l’opérateur de résolution de portée pour la fonction SetPoint Il est déclaré dans la librairie graph etla classe CSpiro. Pour que le compilateur appelle la fonction requise, nous l’indiquons explicitement à l'aide de l'action :: et donnons le nom du fichier.

  Graph::SetPoint(0, m_sID+"pnt."+string(x)+"."+string(y), 0, x, y, m_clr);

Nous pouvons maintenant inclure le fichier d'en-tête et importer son implémentation dans notre Expert Advisor subséquent.

Ceci peut être schématisé comme suit :

Schéma d’opération avec les méthodes de classes de librairie

Example 5. Using export objects

//--- Spiro.mq5 - the target file of the Expert Advisor

//--- importing some functions
#import "Graph.ex5" 
  void SetLabel(long achart, string name, int wnd, string text, color clr,
               int x, int y, int corn=0, int fontsize=8, string font="Tahoma");
  void SetEdit(long achart, string name, int wnd, string text, color txtclr, color bgclr, color brdclr, 
              int x, int y, int dx, int dy, int corn=0, int fontsize=8, string font="Tahoma", bool ro=false);
  void SetButton(long achart, string name, int wnd, string text, color txtclr, color bgclr, 
                int x, int y, int dx, int dy, int corn=0, int fontsize=8, string font="Tahoma", bool state=false);
  void HideChart(long achart, color BackClr);
#import

//--- including the chart class
#include <Spiro.mqh> 

//--- importing the object
#import "ISpiro.ex5"
  CSpiro *iSpiro();
#import

//--- object instance
CSpiro *spiro; 
//--- prefix for chart objects
string sID; 
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
void OnInit()
{
  HideChart(0, clrWhite);
  sID="spiro.";
  DrawParam();
//--- object instance created
  spiro=iSpiro(); 
//--- initializing the drawing
  spiro.Init(250, 200, clrBlack, sID);
//--- setting the calculation parameters
  spiro.SetData(100, 30, 40, 0.04, 10);
//--- drawing
  spiro.DrawSpiro(); 
}
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
  delete spiro; // deleting the object
}

En conséquence, vous serez en mesure de modifier les paramètres de l'objet dans le graphique et dessiner le graphique de l'objet



Paramètres graphiques de l’objet


3. Initialisation des Variables dans le fichier .ex5

C’est souvent le cas que votre ISuperClass utilise les variables depuis le fichier include globals.mqh. Ces variables peuvent être comprises de la même manière pour être utilisées dans vos autres fichiers.

Par exemple:

Example 6. Public include file

//--- globals.mqh

#include <Trade\Trade.mqh>
//--- instance of the trade function object
extern CTrade *_trade; 

.L’unique instance de l’objet de _trade est initialisé dans votre programme et pourtant il est utilisée dans la classe cachée ISuperClass.

A cet effet, un pointeur vers l'objet que vous avez créé doit être transmis de la classeISuperClass au fichier .ex5.

Il est plus facilement réalisable lorsque l'objet est reçu du fichier .ex5, comme ci-dessous :

Example 7. Initialization of variables upon creation of the object

//--- ISuperClass.mq5 –hidden implementation file

#property library
CSuperClass *iSuperClass(CTrade *atrade) export
{
//--- saving the pointer
   _trade=atrade; 
//--- returning the object of the hidden implementation of ISuperClass of the open CSuperClass class
  return(new ISuperClass); 
}
//... the remaining code

Ainsi, toutes les variables requises sont initialisées à la réception de l'objet dans son module.

En fait, il peut y avoir beaucoup de variables globales publiques qui peuvent être de différents types. Ceux qui sont désireux de modifier l’en-tête de la fonctioniSuperClass tout le temps, devraient mieux créer une classe spéciale cumulant toutes les variables globales et fonctions travaillant avec celui-ci.

Example 8. Public include file

//--- globals.mqh
#include <Trade\Trade.mqh>

//--- trade "object"
extern CTrade *_trade; 
//--- name of the Expert Advisor of the system
extern string _eaname; 

//+------------------------------------------------------------------+
//| class __extern                                                   |
//+------------------------------------------------------------------+
class __extern // all extern parameters for passing between the ex5 modules are accumulated here
{
public:
//--- the list of all public global variables to be passed
//--- trade "object"
  CTrade *trade; 
//--- name of the Expert Advisor of the system
  string eaname; 
    
public:
  __extern() { };
  ~__extern() { };

//--- it is called when passing the parameters into the .ex5 file
  void Get() { trade=_trade; eaname=_eaname; };  // getting the variables

 //--- it is called in the .ex5 file
  void Set() { _trade=trade; _eaname=eaname; };  // setting the variables
                                                       
};
//--- getting the variables and pointer for passing the object into the .ex5 file
__extern *_GetExt() { _ext.Get(); return(GetPointer(_ext)); } 

//--- the only instance for operation
extern __extern _ext; 
Le fichier ISuperClass.mq5 sera implémenté comme suit:
Example 9.

//--- ISuperClass.mq5 –hidden implementation file

#property library
CSuperClass *iSuperClass(__extern *aext) export
{
//--- taking in all the parameters
  aext.Set();
//--- returning the object
  return(new ISuperClass); 
}
//--- ... the remaining code

L'appel de fonction va maintenant être transformé en une forme simplifiée et, ce qui est le plus important, extensible.

Example 10. Using export objects in the presence of public global variables

//--- including global variables (usually located in SuperClass.mqh)
#include "globals.mqh"    

//--- including the public header class
#include "SuperClass.mqh" 
//--- getting the hidden implementation object
#import "ISuperClass.ex5"
  CSuperClass *iSuperClass();
#import

//+------------------------------------------------------------------+
//| Script program start function                                    |
//+------------------------------------------------------------------+
void OnStart()
{
//--- creating the hidden implementation object providing for the passing of all parameters
  CSuperClass *sc=iSuperClass(_GetExt()); 
  //--- ... the remaining code
}


4. Héritage des Classes d'Exportation

Vous devez déjà avoir compris que cette façon d'exporter des objets implique que l'héritage direct et simple est hors de question. L'exportation de l'objet d'implémentation caché suggère que l'objet lui-même est le dernier maillon de la chaîne d'héritage et est celui qui peut finalement être utilisé.

Dans le cas général vous pouvez créer une "émulation" d'héritage en écrivant une classe intermédiaire supplémentaire. Et ici, nous aurons bien sûr besoin de polymorphisme et de virtualité.

Example 11. Emulation of inheritance of hidden classes

//--- including the public header class
#include "SuperClass.mqh" 

//--- getting the hidden implementation object
#import "ISuperClass.ex5"
  CSuperClass *iSuperClass();
#import

class _CSuperClass
{
public:
//--- instance of the hidden implementation object
  CSuperClass *_base;
public:
//--- constructor
  _CSuperClass() {  _base=iSuperClass(_GetExt()); };
//--- destructor
  ~_CSuperClass() { delete _base; };
//--- further followed by all functions of the base CSuperClass class
//--- working function called from the hidden implementation object
  virtual int func(int a, int b) { _base.func(a,b); }; 
};

La seule question ici est l’accès aux variables de CSuperClass. Comme nous pouvons le constater, ils ne figurent pas dans la déclaration du descendant et se trouvent dans la variable_base. Habituellement, cela n'affecte pas la convivialité à condition qu'il existe une classe d'en-têteSuperClass.mqh.

Naturellement, si vous êtes principalement concentré sur les fonctions de savoir-faire, vous n’êtes pas obligé de créer un emballeur ISuperClassà l’égard d’eux en avance. Il suffira d'exporter ces fonctions de savoir-faire et de laisser les développeurs extérieurs créer leurs propres classes emballeur dont il sera ensuite facile d'hériter.

Ainsi, lors de la préparation de vos développements pour d'autres développeurs, vous devrez prendre soin de créer tout un ensemble de fonctions d'export nécessaires, de fichiers et de classes .mqh et .ex5 :
  1. Exportation de fonctions indépendantes des classes
  2. Fichiers d'en-tête .mqh et leurs implémentations .ex5
  3. Initialisation des variables dans les fichiers .ex5


5. Édition des Bibliothèques ex5

En novembre 2011, MetaQuotes a commencé à fournir un accès à un référentiel de fichiers. Davantage sur ça est disponible dans annonce.

Ce référentiel vous permet de stocker vos développements et, ce qui est plus important, d'en donner accès à d'autres développeurs. Cet outil vous permettra de publier facilement de nouvelles versions de vos fichiers afin d'assurer un accès rapide à ceux-ci pour les développeurs susceptibles d'utiliser ces fichiers.

De surcroît, le site web de la société vous offre l’opportunité de proposer vos propres bibliothèques de fonction dans leMarchéà titre commercial ou gratuit.


Conclusion

Vous savez maintenant créer des bibliothèques ex5 avec export de leurs fonctions ou objets de classe et pouvez mettre en pratique vos connaissances. Toutes ces ressources vous permettront d'établir une coopération plus étroite avec d'autres développeurs : pour travailler sur des projets communs, les promouvoir sur le Marché ou donner accès aux fonctions de la bibliothèque ex5.


Traduit du russe par MetaQuotes Ltd.
Article original : https://www.mql5.com/ru/articles/362

Fichiers joints |
spiro.zip (3.91 KB)
La Dernière Croisade La Dernière Croisade
Jetez un œil à votre terminal de trading. Quels moyens de présentation des prix pouvez-vous voir? Barres, chandeliers, lignes. Nous courons après le temps et les prix alors que nous ne profitons que des prix. Doit-on seulement prêter attention aux prix lors de l'analyse du marché ? Cet article propose un algorithme et un script pour la représentation graphique de points et de chiffres («zéros et croix  ») Une attention particulière est accordée à divers modèles de prix dont l'utilisation pratique est décrite dans les recommandations fournies.
Sécurisation du code MQL5 : Protection par mot de passe, générateurs de clés, délais, licences à distance et techniques avancées de cryptage des clés de licence EA Sécurisation du code MQL5 : Protection par mot de passe, générateurs de clés, délais, licences à distance et techniques avancées de cryptage des clés de licence EA
La plupart des développeurs doit de sécuriser leur code. Cet article présentera différentes manières de protéger le logiciel MQL5 - il présente des méthodes pour fournir des fonctionnalités de licence aux scripts, aux Expert Advisors et aux indicateurs MQL5. Il couvre la protection par mot de passe, les générateurs de clés, la licence de compte, l'évaluation du délai et la protection à distance à l'aide d'appels MQL5-RPC.
AutoElliottWaveMaker - Outil MetaTrader 5 pour l'analyse semi-automatique des vagues d'Elliott AutoElliottWaveMaker - Outil MetaTrader 5 pour l'analyse semi-automatique des vagues d'Elliott
L'article fournit une revue d'AutoElliottWaveMaker - le premier développement pour l'analyse d'Elliott Wave dans MetaTrader 5 qui représente une combinaison d'étiquetage de vague manuel et automatique. L'outil d'analyse des vagues est écrit exclusivement en MQL5 et n'inclut pas les bibliothèques dll externes. C'est une autre preuve que des programmes sophistiqués et intéressants peuvent (et doivent) être élaborés en MQL5.
Trademinator 3 : Montée des Machines de Trading Trademinator 3 : Montée des Machines de Trading
Dans l’article « Dr. Tradelove... » nous avons créé un Expert Advisor, qui optimise indépendamment les paramètres d’un système de trading présélectionné. De plus, nous avons décidé de créer un Expert Advisor qui peut non seulement optimiser les paramètres d’un système de trading sous-jacent à l’EA, mais également sélectionner le meilleur des systèmes de trading. Voyons ce qui peut en découler...