Domande dai principianti MQL5 MT5 MetaTrader 5 - pagina 1264

 
Salve.Sono stato ispiratodalla lezione " Using Structures for Effective Program Development"e ho creato una semplice struttura come questa in MT5.
#property copyright "Copyright 2020, MetaQuotes Software Corp."
#property link      "https://www.mql5.com"
#property version   "1.00"
//+------------------------------------------------------------------+
#include <Trade\PositionInfo.mqh>
#include <Trade\OrderInfo.mqh>
#include <Trade\Trade.mqh>
#include <Trade\SymbolInfo.mqh>
#include <Trade\AccountInfo.mqh>
#include <Trade\DealInfo.mqh>
#include <Expert\Money\MoneyFixedMargin.mqh>

CPositionInfo      m_position;// object of CPositionInfo class
COrderInfo         m_order;   // object of COrderInfo class
CTrade             m_trade;   // object of CTrade class
CSymbolInfo        m_symbol;  // object of CSymbolInfo class
CAccountInfo       m_account; // object of CAccountInfo class
CDealInfo          m_deal;    // object of CDealInfo class
CMoneyFixedMargin *m_money;   // object of CMoneyFixedMargin class
//+------------------------------------------------------------------+
//| Structure Positions                                              |
//+------------------------------------------------------------------+
struct STRUCT_POSITION
  {
   ENUM_POSITION_TYPE type;       // тип позиции
   ulong              ticket;     // тикет позиции
   long               identifier; // идентификатор
   long               magic;      // магический номер
   double             volume;     // объем позиции
   double             open_price; // цена открытия
   datetime           open_time;  // время открытия
   double             profit;     // профит позиции
   double             comission;  // комиссия
   double             swap;       // своп
   string             comment;    // комментарий
   
   void               GetCurrentPositionProperty();
  };
  STRUCT_POSITION StrPositionArray[];
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
  {
//---
   
//---
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
  {
//---
   
  }
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
void OnTick()
  {
//---
   STRUCT_POSITION.GetCurrentPositionProperty();
  }
//+------------------------------------------------------------------+
//---Заполнение массива свойств позиций                              +
//+------------------------------------------------------------------+
void STRUCT_POSITION::GetCurrentPositionProperty(void)
{   
   ZeroMemory(this);
   int pos_total = PositionsTotal();
   ArrayResize(StrPositionArray,pos_total,1000);
   for(int i=0; i<pos_total; i++)
      {
         if(m_position.SelectByIndex(i))
            {
               StrPositionArray[i].ticket     = m_position.Ticket();                  // тикет позиции
               StrPositionArray[i].identifier = m_position.Identifier();              // идентификатор
               StrPositionArray[i].magic      = m_position.Magic();                   // магический номер
               StrPositionArray[i].comment    = m_position.Comment();                 // комментарий
               StrPositionArray[i].type       =(ENUM_POSITION_TYPE)m_position.PositionType();// тип позиции
               StrPositionArray[i].volume     = m_position.Volume();                  // объем позиции
               StrPositionArray[i].open_price = m_position.PriceOpen();               // цена открытия
               StrPositionArray[i].open_time  = m_position.Time();                    // время открытия
               StrPositionArray[i].profit     = m_position.Profit();                  // профит позиции
               StrPositionArray[i].comission  = m_position.Commission();              // комиссия
               StrPositionArray[i].swap       = m_position.Swap();                    // своп
            }
      } 
} 
//+------------------------------------------------------------------+

Nella struttura

POSIZIONE_STRUTTURA

la struttura contiene il metodo

GetCurrentPositionProperty(void)

che calcola e assegna valori agli elementi della struttura. Definire il corpo del metodo al di fuori della struttura. Per farlo, usate l'operazione di risoluzione del contesto (::).

In OnTick() chiamiamo la funzione:

void OnTick() { //--- STRUCT_POSITION.GetCurrentPositionProperty(); }

E qui otteniamo un errore:

'.' - nome atteso eSower_and_Gather_5.mq5 69 19
Non so dove sia andato storto, per favore aiutatemi.

 
Sergey Voytsekhovsky:

'.' - nome previsto eSower_and_Gather_5.mq5 69 19

Cos'è la linea 69 19? Si prega di pubblicare la linea di codice 69 e di specificare dove si trova la posizione 19. Sarà immediatamente chiaro dove si trova l'errore.

 
Vladimir Karputov:

Cos'è la linea 69 19? Codice postale linea 69 e specificare dove si trova la 19a posizione. Sarà immediatamente chiaro dove si trova l'errore.

STRUCT_POSITION.GetCurrentPositionProperty();

È evidenziato in rosso nel post sopra. Grazie per la sua pronta risposta.

 
Vladimir Karputov:

Cos'è la linea 69 19? Codice postale linea 69 e specificare dove si trova la 19a posizione. Sarà immediatamente chiaro dove si trova l'errore.

Questo è un punto che deve dare accesso a una funzione che a sua volta utilizza il contesto della struttura. Ma non riesco a capire perché non funziona.

 
Sergey Voytsekhovsky:

è evidenziato in rosso nel post sopra. Grazie per la sua pronta risposta.

STRUCT_POSITION' è un TIPO DI DATI. Dovete creare una variabile con questo tipo e poi chiamare VARIABLE.GetCurrentPositionProperty();

Документация по MQL5: Основы языка / Типы данных
Документация по MQL5: Основы языка / Типы данных
  • www.mql5.com
Любая программа оперирует данными. Данные могут быть различных типов в зависимости от назначения. Например, для доступа к элементам массива используются данные целочисленного типа. Ценовые данные имеют тип двойной точности с плавающей точкой. Это связано с тем, что в языке MQL5 не предусмотрено специального типа для ценовых данных. Данные...
 
Sergey Voytsekhovsky:

Questo è il punto che dovrebbe dare accesso alla funzione, che a sua volta utilizza il contesto della struttura. Ma perché non funziona non riesco a capire.

Codice: (basta chiamare una funzione - funzione EA, non un metodo di struttura - che ha più senso)

//+------------------------------------------------------------------+
//|                                                      ProjectName |
//|                                      Copyright 2020, CompanyName |
//|                                       http://www.companyname.net |
//+------------------------------------------------------------------+
#property copyright "Copyright 2020, MetaQuotes Software Corp."
#property link      "https://www.mql5.com"
#property version   "1.00"
//---
#include <Trade\PositionInfo.mqh>
#include <Trade\OrderInfo.mqh>
#include <Trade\Trade.mqh>
#include <Trade\SymbolInfo.mqh>
#include <Trade\AccountInfo.mqh>
#include <Trade\DealInfo.mqh>
#include <Expert\Money\MoneyFixedMargin.mqh>
//---
CPositionInfo      m_position;// object of CPositionInfo class
COrderInfo         m_order;   // object of COrderInfo class
CTrade             m_trade;   // object of CTrade class
CSymbolInfo        m_symbol;  // object of CSymbolInfo class
CAccountInfo       m_account; // object of CAccountInfo class
CDealInfo          m_deal;    // object of CDealInfo class
CMoneyFixedMargin *m_money;   // object of CMoneyFixedMargin class
//+------------------------------------------------------------------+
//| Structure Positions                                              |
//+------------------------------------------------------------------+
struct STRUCT_POSITION
  {
   ENUM_POSITION_TYPE type;       // тип позиции
   ulong              ticket;     // тикет позиции
   long               identifier; // идентификатор
   long               magic;      // магический номер
   double             volume;     // объем позиции
   double             open_price; // цена открытия
   datetime           open_time;  // время открытия
   double             profit;     // профит позиции
   double             comission;  // комиссия
   double             swap;       // своп
   string             comment;    // комментарий

   void               GetCurrentPositionProperty();
  };
STRUCT_POSITION StrPositionArray[];
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
  {
//---
//---
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
  {
//---
  }
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
void OnTick()
  {
//---
   GetCurrentPositionProperty();
  }
//+------------------------------------------------------------------+
//| Заполнение массива свойств позиций                               |
//+------------------------------------------------------------------+
void GetCurrentPositionProperty(void)
  {
   int pos_total = PositionsTotal();
   ArrayResize(StrPositionArray,pos_total,1000);
   for(int i=0; i<pos_total; i++)
     {
      if(m_position.SelectByIndex(i))
        {
         StrPositionArray[i].ticket     = m_position.Ticket();                  // тикет позиции
         StrPositionArray[i].identifier = m_position.Identifier();              // идентификатор
         StrPositionArray[i].magic      = m_position.Magic();                   // магический номер
         StrPositionArray[i].comment    = m_position.Comment();                 // комментарий
         StrPositionArray[i].type       =(ENUM_POSITION_TYPE)m_position.PositionType();// тип позиции
         StrPositionArray[i].volume     = m_position.Volume();                  // объем позиции
         StrPositionArray[i].open_price = m_position.PriceOpen();               // цена открытия
         StrPositionArray[i].open_time  = m_position.Time();                    // время открытия
         StrPositionArray[i].profit     = m_position.Profit();                  // профит позиции
         StrPositionArray[i].comission  = m_position.Commission();              // комиссия
         StrPositionArray[i].swap       = m_position.Swap();                    // своп
        }
     }
  }
//+------------------------------------------------------------------+
 
Vladimir Karputov:

STRUCT_POSITION' è un TIPO DI DATI. Dovete creare un oggetto con questo tipo e poi chiamare OBJECT.GetCurrentPositionProperty();

Provato. Tale oggetto viene creato, dichiarato subito dopo la dichiarazione dell'elemento

StrPositionArray[].

Se lo metti in OnTick

void OnTick()
  {
//---
   StrPositionArray[].GetCurrentPositionProperty();
  }

otteniamo un errore:

']' - espressione prevista eSower_and_Gather_5.mq5 69 21

Questa è la stessa linea, solo la seconda parentesi, quella appena prima del punto.
 
Vladimir Karputov:

Codice: (basta chiamare una funzione - funzione EA, non un metodo di struttura - che ha più senso)

Quindi usare :: era un'idea inutile?

Allora perché hai scritto la funzione

GetCurrentPositionProperty()

all'interno della struttura? Riempirebbe la struttura senza alcun riempimento al suo interno, vero? Per favore chiarite, sono confuso, forse questa è una funzione obsoleta, dovrei dimenticarla?

 
Sergey Voytsekhovsky:

Quindi usare :: è stata una perdita di tempo?

Allora perché scrivere una funzione

all'interno della struttura? Cioè, riempirà perfettamente la struttura anche senza. Per favore, chiarisci, sono confuso, forse questa è un'idea obsoleta che dovrebbe essere dimenticata.

Copia-incolla. C'è una linea rimasta dopo il copia-incolla.

Dovrebbe essere così (non ci sono metodi all'interno della struttura)

//+------------------------------------------------------------------+
//| Structure Positions                                              |
//+------------------------------------------------------------------+
struct STRUCT_POSITION
  {
   ENUM_POSITION_TYPE type;       // тип позиции
   ulong              ticket;     // тикет позиции
   long               identifier; // идентификатор
   long               magic;      // магический номер
   double             volume;     // объем позиции
   double             open_price; // цена открытия
   datetime           open_time;  // время открытия
   double             profit;     // профит позиции
   double             comission;  // комиссия
   double             swap;       // своп
   string             comment;    // комментарий
  };
STRUCT_POSITION StrPositionArray[];
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
  {
 
Vladimir Karputov:

Copia-incolla. C'è una linea lasciata dopo il copia-incolla.

Dovrebbe essere così (non ci sono metodi all'interno della struttura)

Beh, ho speso tanto tempo per la lezione. Anche se era per MT4, è stato presentato lì come un trucco, quindi ecco un estratto del testo:

1
2
3
4
5
6
7
8
9
10
11
12
struttura stato
{
int buy_count; // numero di ordini di acquisto
int sell_count; // numero di ordini di vendita
double buy_bottom_price; //prezzo di apertura dell'ordine di acquisto più basso
double sell_top_price; //prezzo di apertura dell'ordine di vendita più alto
doppio profitto; // profitto di tutti gli ordini
// metodo per raccogliere informazioni sullo stato dell'account
// e aggiornare gli elementi della struttura
void Refresh() ;
} Stato;

La struttura ha un metodo Refresh() che calcola e assegna valori agli elementi della struttura. Definiamo il corpo del metodo fuori dalla struttura. Per fare questo, usiamo l'operazione di risoluzione del contesto (::). Il contesto è un descrittore (nome) della struttura:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
//+------------------------------------------------------------------+
//| Il metodo raccoglie informazioni sullo stato attuale dell'account.
//| e aggiorna i campi pertinenti della struttura |
//+------------------------------------------------------------------+
void state::Refresh( void )
{
//zero i campi numerici della struttura
ZeroMemory( questo );
for ( int i=OrdersTotal()-1; i>=0; i--)
se (OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
if (OrderSymbol()==_Symbol && OrderMagicNumber()==Magic)
{
double OpenPrice=OrderOpenPrice();
profitto+=OrderProfit()+OrderCommission()+OrderSwap();
interruttore (OrderType())
{
caso OP_BUY:
buy_count++;
se (OpenPrice<buy_bottom_price || buy_bottom_price==0)
buy_bottom_price=OpenPrice;
pausa ;
caso OP_SELL:
sell_count++;
se (OpenPrice>sell_top_price || sell_top_price==0)
sell_top_price=OpenPrice;
pausa ;
}
}
}

Notate che nel corpo del metodo ci riferiamo agli elementi della struttura senza usare un punto, poiché abbiamo usato l'operazione di risoluzione del contesto. I campi numerici sono azzerati da ZeroMemory() con la parola chiave this prima di aggiornarli all'inizio del corpo del metodo, quindi la struttura passa un riferimento a se stessa.

Il codice principale di EA all'interno del gestore OnTick() sarà ora simile a questo

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
//+------------------------------------------------------------------+
//| Funzione tick esperto|
//+------------------------------------------------------------------+
void OnTick()
{
for ( int i=0; i<2000; i++)
{
doppio b=MathSqrt(i);
}
// aprire nuovi ordini e prendere profitto solo all'apertura di una nuova barra
se (IsNewBar())
{
// ottenere un nuovo segnale
int Signal=GetSignal();
// esce immediatamente dalla funzione se il segnale non è stato generato sulla barra chiusa.
se (Segnale<0)
ritorno ;
//aggiornare la struttura
State.Refresh(); // (!!! )