Creating object with "new" operator as a global variable, a good idea or bad idea?

 

Quick question.  I am trying to write an EA that will record datetime and bid price data at each tick tick, and store this data only for the most recent x number of seconds. (IE the ea uses the tick data from the previous 20 seconds to make decisions on trading.)   Since I do not know how many ticks there will be in this amount of time, I thought I would use in the global variables - dynamic arrays CArrayDouble object for the bid prices and CArrayInt object for the datetimes.   These dynamic arrays would store data at each new tick and delete tick data that is older than x number of seconds. Is this a good idea?  Or will it cause memory leak or something else bad?  Here is my code so far:

 

//+------------------------------------------------------------------+
//|                                                      Scalper.mq5 |
//|                                                              Joe |
//|                                              http://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Joe"
#property link      "http://www.mql5.com"
#property version   "1.00"

#include <Arrays\ArrayInt.mqh>
#include <Arrays\ArrayDouble.mqh>
#include <Trade\Trade.mqh>
  
//--- input parameters

//---global variables
CArrayDouble *bid_array=new CArrayDouble;
CArrayInt    *seconds_array=new CArrayInt;

//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
  {  
   if(bid_array==NULL)
     {
      Print("Object create error");
      return(INIT_FAILED);
     }
//--- 
   if(seconds_array==NULL)
     {
      Print("Object create error");
      return(INIT_FAILED);
     }     
//---
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
  {
//--- delete arrays
   delete bid_array;
   delete seconds_array;  
  }
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
void OnTick()
  {
   
 
//--- Use arrays to record bid prices using the Add function
//--- for new tick data and the Delete function to delete tick data 
//--- older than x number of seconds
//--- . . .

   
  }
//+------------------------------------------------------------------+
 
oneilljo:

Quick question.  I am trying to write an EA that will record datetime and bid price data at each tick tick, and store this data only for the most recent x number of seconds. (IE the ea uses the tick data from the previous 20 seconds to make decisions on trading.)   Since I do not know how many ticks there will be in this amount of time, I thought I would use in the global variables - dynamic arrays CArrayDouble object for the bid prices and CArrayInt object for the datetimes.   These dynamic arrays would store data at each new tick and delete tick data that is older than x number of seconds. Is this a good idea?  Or will it cause memory leak or something else bad?  Here is my code so far:

In my opinion, there is no technical issue with your approach but maybe a logical one. What you need as dynamic are the arrays not the object itself. So you can use :

//---global variables
CArrayDouble bid_array;
CArrayInt    seconds_array;

However if you keep pointers, I suggest you the following modification :

int OnInit()
  {  
   if(CheckPointer(bid_array)==POINTER_INVALID)
     {
      Print("Object create error");
      return(INIT_FAILED);
     }
//--- 
   if(CheckPointer(seconds_array)==POINTER_INVALID)
     {
      Print("Object create error");
      return(INIT_FAILED);
     }     
...
 
oneilljo:

Quick question.  I am trying to write an EA that will record datetime and bid price data at each tick tick, and store this data only for the most recent x number of seconds. (IE the ea uses the tick data from the previous 20 seconds to make decisions on trading.)   Since I do not know how many ticks there will be in this amount of time, I thought I would use in the global variables - dynamic arrays CArrayDouble object for the bid prices and CArrayInt object for the datetimes.   These dynamic arrays would store data at each new tick and delete tick data that is older than x number of seconds. Is this a good idea?  Or will it cause memory leak or something else bad?  Here is my code so far:

Using dynamic arrays will not cause memory leaks, unless MT5 has a bug.  It should be handling the dynamic part of the array and controlling the memory allocation.

One slightly disconnected point,  you might want to consider how and if you want to record missed ticks . . . you will miss some ticks and you can determine that you have missed ticks,  the question is do you want to keep track of that fact in your array ? 

 
Thanks for the advice guys!  Angevogageur - I will use those global variables you recommended.  RaptorUK, I am not worried about missed ticks for now.  I have another question though,  what type of dynamic array should I use to store the datetime of each tick?  I tried CArrayInt, and also tried CArrayObj to store MqlDatetime Objects.  Neither of theses approaches worked.  What would you recommend?  Should I convert the datetime from TimeCurrent() to a string, store at in CArrayString, then reconvert each element back to a datetime using StringToTime() when I need to work with each element?
Documentation on MQL5: Conversion Functions / StringToTime
Documentation on MQL5: Conversion Functions / StringToTime
  • www.mql5.com
Conversion Functions / StringToTime - Documentation on MQL5
 
oneilljo:
Thanks for the advice guys!  Angevogageur - I will use those global variables you recommended.  RaptorUK, I am not worried about missed ticks for now.  I have another question though,  what type of dynamic array should I use to store the datetime of each tick?  I tried CArrayInt, and also tried CArrayObj to store MqlDatetime Objects.  Neither of theses approaches worked.  What would you recommend?  Should I convert the datetime from TimeCurrent() to a string, store at in CArrayString, then reconvert each element back to a datetime using StringToTime() when I need to work with each element?
Why not simply declare the array as type datetime and then handle the resizing yourself using a combination of ArraySize() and ArrayResize() ?  each time you need to add an element to the array resize it with a size of ArraySize() + 1
 
oneilljo:
Thanks for the advice guys!  Angevogageur - I will use those global variables you recommended.  RaptorUK, I am not worried about missed ticks for now.  I have another question though,  what type of dynamic array should I use to store the datetime of each tick?  I tried CArrayInt, and also tried CArrayObj to store MqlDatetime Objects.  Neither of theses approaches worked.  What would you recommend?  Should I convert the datetime from TimeCurrent() to a string, store at in CArrayString, then reconvert each element back to a datetime using StringToTime() when I need to work with each element?
There is no class for datetime array, as datetime is actually an int. So you can normally use CArrayInt. Or follow RaptorUk advice, don't use a class, use datetime array and resize it yourself.
 
Thanks for the advice guys, I ended up using ArrayResize() and ArrayCopy() to do the job.
Documentation on MQL5: Array Functions / ArrayResize
Documentation on MQL5: Array Functions / ArrayResize
  • www.mql5.com
Array Functions / ArrayResize - Documentation on MQL5
 
Alain Verleyen:
There is no class for datetime array, as datetime is actually an int. So you can normally use CArrayInt. Or follow RaptorUk advice, don't use a class, use datetime array and resize it yourself.

Hi, are you sure CArrayInt is conviniet, if Int has 4 bytes and datetime is of 8 bytes? Or is it necessary first to structure datetime some how?

 
BOCTOK:

Hi, are you sure CArrayInt is conviniet, if Int has 4 bytes and datetime is of 8 bytes? Or is it necessary first to structure datetime some how?

You are answering to a more than 6 years post. In the meantime a lot has changed (datetime was 4 bytes at that time).

With 4 bytes a datetime can manage date up to 2038, up to you to see if you can live with that or not. If not use CArrayLong.

 
Alain Verleyen:

You are answering to a more than 6 years post. In the meantime a lot has changed (datetime was 4 bytes at that time).

With 4 bytes a datetime can manage date up to 2038, up to you to see if you can live with that or not. If not use CArrayLong.

2038 is enough :) thanks!
Reason: