Running EA once at the start of each bar

 

Hi all hero traders and tradettes.

I want my EA to run once per bar. I have heard of complicated ways to do this, but I may have figured out a simple way. Setting a global datetime variable and an if statement making the program execute only if the datetime of the current bar is different to the datetime of the bar the program was last run on (i.e. the last bar). To get more accurate (but slightly less responsive) data, I have set the shift for EMAs back one bar, as otherwise they would get values from a bar (current one) with only 1 tick of data.

Declare a global variable:

datetime LastRunTime;

At the very beginning of the start function:

if(LastRunTime != iTime(NULL,0,0))

{

-whole program here-

LastRunTime = iTime(NULL,0,0);

}

Is this a good way to do it? If so, is it okay to backtest using open prices only? If not, can someone point me to a way to do this, so that backtesting can be done with open prices only (if possible)?

Thanks again. I have attached my EA for anyone to have a look at if they want, it appears to profitable so far.

Files:
gr2.mq4  14 kb
 

NM

That's the general idea :)

The often used way is this - it gives more flexibility if some code needs to run each tick or once-per-bar

static bool IsNewBar;
static datetime LastBarOpenAt;


start()
 {

 if(LastBarOpenAt == Time[0]) // This tick is not in new bar
    {
     IsNewBar=false;
    }
  else
    {
      LastBarOpenAt = Time[0];
      IsNewBar = true;    
    }

// rest of code where you can check value of IsNewBar
// ................................................................

// ................................................................

 }

Good Luck

-BB-

 

"static" isn't necessary (does that compile) for global variables only for local.

Simplify using bool

start()
 {
  bool IsNewBar = LastBarOpenAt != Time[0];
  if (IsNewBar){ LastBarOpenAt = Time[0]; ...
But you don't even need the bool
int     start(){     static datetime Time0;
    if (Time0 == Time[0]) return(0); Time0 = Time[0];
   ...
 

Any reason this wouldnt work ?

static int bars=Bars;

if(bars != Bars)

{
do something;

bars=Bars;

}

 

Thanks for suggestions, BarrowBoy, the code you gave is really good. Great to be able to run some things once a bar and other things tick by tick.


If the whole thing is running once per bar, as long as modeling quality is very good, is it accurate to backtest using open prices only?

Thanks again.

 
SDC:

Any reason this wouldnt work ?

static int bars=Bars;

if(bars != Bars)

{
do something;

bars=Bars;
 

}

Yes. Bars eventually reaches a maximum value (as set in the MT4 options.) This method would eventually cause the statement block inside the "if" to never execute.
 
Bars is unreliable. Volume is unreliable. Always use time.
 

I use something like this:

datetime now;

int start()
{
   if( now != Time[0] )
   {
      now = Time[0];
   ...once per bar code goes here...
   }

...once per tick code goes here...

return (0) ;

}

There is also the option of coding a start() function that never returns and uses RefreshRates() in order to retrieve current quotes.

 
hi can you help me on this,i want to execute on bar opening but am getting errors like NewBar undeclaired identifier and iBarShift wrong parameters
    
   if(CheckOncePerBar == true)
     {
       int iBarShift = 1;
       if(CurrentTimeStamp != Time[0])
         { 
           CurrentTimeStamp = Time[0];
          bool NewBar = true; 
         }
       else
        NewBar = false; 
     }
   else 
     {
       NewBar = true;
       iBarShift = 0;
     }