Learning mql4. Intro and questions of a student. - page 2

 
azFIN wrote >>

Ickyrus,

Thanks for the response. I'm still not certain on how I go about making sure I'm using the correct double values for my calculations. What I mean is when I print just the value of Bid, there are only 4 digits after the decimal point. I'm trying to figure out how I should write everything so that both my calculations and the values that get sent to the dealers server are correct. The only way I could get it to print all 5 digits after the decimal was by using the code pasted above with the DoubleToStr. How should I write that so that the correct values are being used within the program and displayed correctly?

Where posible use integer arithmatic - it a little faster than floating point. For all averaging and statistical calculations use double. Where sending values to the dealer use NormalisedDouble function there is a global variable that tells you how many decimal places the dealer uses. In your actual program, unless appropriate to round, keep your floating point numbers as unrounded as possible.

Do a Google search for computer arithmatic for a better understanding Wickipedia should have a good article on it.

What you seem to be worying about is the displaying of the internal representation of a floating point number - just leave that to the print function.

 
Bid will always be normalized to the correct precision. By definition it is normalized to 'Digits'. So when you are working with a 5 digit broker, Bid will have 5 digits of precision. Always. The only reason you see Bid output with 4 digits is due to a quirk of the Print(), Alert() and Comment() functions which default their output to 4 digits. By using the DoubleToStr() function with a value of 5, you are merely exposing the existing 5 digits of precision of your Bid in the printed output. CB
 

Sample of absolutely precise price operations

In the future all my internal prices presentations and operations will be integer

 

Thanks for answering my question guys. Working all day today but looking forward to getting back to working on writing my first programs tomorrow. I'll let you know how it goes as I progress.

 

Been working on a MA crossover indicator for practice. Was hoping for some more pointers and advice as a I progress here. A few things I'm unsure of is if there is a better way to write the counted_bars/iHistory lines of the DrawMA() function? I don't understand why I can't jsut remove those lines and set int i equal to iHistory. How do I make sure the objects I'm creating to mark the crossovers are centered right on or around the crossover point? I'm still really trying to make sure I understand everything as I move on so any suggestions about anything I'm missing or should have written in a better way are much appreciated. Thanks.

//+------------------------------------------------------------------+
//|                                                 _MA + IB Ind.mq4 |
//|                      Copyright © 2010, MetaQuotes Software Corp. |
//|                                        http://www.metaquotes.net |
//+------------------------------------------------------------------+
#property copyright "Copyright © 2010, MetaQuotes Software Corp."
#property link      "http://www.metaquotes.net"

#property indicator_chart_window
#property indicator_buffers 2
#property indicator_color1 Blue
#property indicator_color2 Red

extern int iHistory = 100;                            //Bars to use
extern double MA_Period_1 = 50;                       //Fast MA
extern double MA_Period_2 = 200;                      //Slow MA

double Line_0[], Line_1[];                            

//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int init()
  {
   
  SetIndexBuffer(0,Line_0);                  
  SetIndexBuffer(1,Line_1);

   return(0);
  }

//+------------------------------------------------------------------+
//| Custom indicator iteration function                              |
//+------------------------------------------------------------------+
int start()
  {
  
   DrawMA();                                          //Draw MA function
   ErrorCheck();                                      //Check for errors
                
   return(0);
  }
  
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function                       |
//+------------------------------------------------------------------+
int deinit()
  {
  
   DeleteObjects();                                   //Delete objects on close

   return(0);
  }
    
//+------------------------------------------------------------------+


   void DeleteObjects()
     {
      for (int i=iHistory; i>=0; i--)
         {
          if (ObjectFind("signal" + i) != -1)
            {
             ObjectDelete("signal" + i);
            }     
         }
      }
   
//-------------------------------------------------------------------

   void DrawMA()
      {
       int    i, counted_bars;
   
      counted_bars = IndicatorCounted();
      i=Bars-counted_bars-1;
      if(i>iHistory) i = iHistory;
   
      double MA_1, MA_2, x1, x2, y1, y2;
   
      while(i>=0)
         {
       
          Print("Checking bar ",i);
          MA_1=iMA(0,0,MA_Period_1,0,MODE_LWMA,PRICE_TYPICAL,i);             //MA 1
            //Print("MA_1 = ",MA_1," @ bar: ",i);
          Line_0[i]=MA_1;
       
          MA_2=iMA(0,0,MA_Period_2,0,MODE_LWMA,PRICE_TYPICAL,i);             //MA 2
          Line_1[i]=MA_2;
            //Print("MA_2 = ",MA_2," @ bar: ",i);
       
          x1=Line_0[i+1];                                                    //MA 1 - previous bar 
          x2=Line_0[i];                                                      //MA 1 - current bar 
          y1=Line_1[i+1];                                                    //MA 2 - previous bar 
          y2=Line_1[i];                                                      //MA 2 - current bar 
       
          if ((x1>y1 && x2<y2) || (x1<y1 && x2>y2))                          //if there was a crossover
           {                                                                           //then create object to mark it 
            ObjectCreate("signal" + i,OBJ_ARROW,0,Time[i],Line_0[i]);
            //ObjectSetText("signal",CharToStr(161),20,"Wingdings",Gold);
            Print("Equal @ bar: ",i);
           }
       
          i--;
         }
      }

//----------------------------------------------------------------

   void ErrorCheck()
      {
       int err = GetLastError();
       if(err != 0)
         Alert("Error: ",err);
      }
 

Ok. Found an error when the crossover was taking place on the current bar and it was trying to create an object that was already there. Fixed that one I think but would still appreciate any suggestions anyone has to improve my first indicator. Thanks

//+------------------------------------------------------------------+
//|                                                 _MA + IB Ind.mq4 |
//|                      Copyright © 2010, MetaQuotes Software Corp. |
//|                                        http://www.metaquotes.net |
//+------------------------------------------------------------------+
#property copyright "Copyright © 2010, MetaQuotes Software Corp."
#property link      "http://www.metaquotes.net"

#property indicator_chart_window
#property indicator_buffers 2
#property indicator_color1 Blue
#property indicator_color2 Red

extern int iHistory = 100;                            //Bars to use
extern double MA_Period_1 = 50;                       //Fast MA
extern double MA_Period_2 = 200;                      //Slow MA

double Line_0[], Line_1[];                            

//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int init()
  {
   
  SetIndexBuffer(0,Line_0);                  
  SetIndexBuffer(1,Line_1);

   return(0);
  }

//+------------------------------------------------------------------+
//| Custom indicator iteration function                              |
//+------------------------------------------------------------------+
int start()
  {
  
   DrawMA();                                          //Draw MA function
   ErrorCheck();                                      //Check for errors
                
   return(0);
  }
  
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function                       |
//+------------------------------------------------------------------+
int deinit()
  {
  
   DeleteObjects();                                   //Delete objects on close

   return(0);
  }
    
//+------------------------------------------------------------------+


   void DeleteObjects()
     {
      for (int i=iHistory; i>=0; i--)
         {
          if (ObjectFind("signal" + i) != -1)
            {
             ObjectDelete("signal" + i);
            }     
         }
      }
   
//-------------------------------------------------------------------

   void DrawMA()
      {
       int    i, counted_bars;
   
      counted_bars = IndicatorCounted();
      i=Bars-counted_bars-1;
      if(i>iHistory) i = iHistory;
   
      double MA_1, MA_2, x1, x2, y1, y2;
   
      while(i>=0)
         {
       
          Print("Checking bar ",i);
          MA_1=iMA(0,0,MA_Period_1,0,MODE_LWMA,PRICE_TYPICAL,i);             //MA 1
            //Print("MA_1 = ",MA_1," @ bar: ",i);
          Line_0[i]=MA_1;
       
          MA_2=iMA(0,0,MA_Period_2,0,MODE_LWMA,PRICE_TYPICAL,i);             //MA 2
          Line_1[i]=MA_2;
            //Print("MA_2 = ",MA_2," @ bar: ",i);
       
          x1=Line_0[i+1];                                                    //MA 1 - previous bar 
          x2=Line_0[i];                                                      //MA 1 - current bar 
          y1=Line_1[i+1];                                                    //MA 2 - previous bar 
          y2=Line_1[i];                                                      //MA 2 - current bar 
       
          if ((x1>y1 && x2<y2) || (x1<y1 && x2>y2))                          //if there was a crossover
           {      
            if (ObjectFind("signal" + i) == -1)                              //check to make sure it hasn't been marked already
               {                                                                     //then create object to mark it 
                ObjectCreate("signal" + i,OBJ_ARROW,0,Time[i],Line_0[i]);
                //ObjectSetText("signal",CharToStr(161),20,"Wingdings",Gold);
                Print("Equal @ bar: ",i);
               }
           }
       
          i--;
         }
      }

//----------------------------------------------------------------

   void ErrorCheck()
      {
       int err = GetLastError();
       if(err != 0)
         Alert("Error: ",err);
      }
 

Would still really appreciate any comments regarding my past posts. Continuing to learn here, have been trying to figure out how to use candle direction as a signal. Been working on trying to figure this out for a while I'm looking for a little advice or where to look for an example. I'm starting with writing an idicator to tell me the direction of each of the last 100 hour bars and the direction of the corresponding daily bars at that time. Really having trouble figuring this one out...

I have some ideas I've been trying to test out such as just using division of hours to determine what day it would be but can't even figure out how to get the hour for the current bar im checking. I'll add the code I was playing around with trying to figure it out. Please help...

   int    i, counted_bars;
   
      counted_bars = IndicatorCounted();
      i=Bars-counted_bars-1;
      if(i>iHistory) i = iHistory;
      
      
      while (i>=0)
      {
      datetime dHour = i;
      Print(i," Hour = ",TimeHour(dHour));  
      i--;
      }
 
Ok. Found an error when the crossover was taking place on the current bar and it was trying to create an object that was already there. Fixed that one I think but would still appreciate any suggestions anyone has to improve my first indicator.
Don't use objects in indicators, an EA can't see them. Place the value in the buffer and use setIndexStyle(0,DRAW_ARROW)
counted_bars = IndicatorCounted();
i=Bars-counted_bars-1;
while(i>=0)
Use the standard code for counting.
int i,counted_bars=IndicatorCounted();
if(counted_bars<0) return(-1);
if(counted_bars>0) counted_bars--;
for(i=Bars-counted_bars-1; i>=0; i--) {
 

Thanks for the response. Been playing around with the suggested idea not to use objects and to rather use buffers. I know I am close but can't seem to get this to put the arrow only on the necessary points. Tried all sorts of ways for a couple hours again and cant seem to get it. Any suggestions? Thanks.

//+------------------------------------------------------------------+
//|                                                 _MA + IB Ind.mq4 |
//|                      Copyright © 2010, MetaQuotes Software Corp. |
//|                                        http://www.metaquotes.net |
//+------------------------------------------------------------------+
#property copyright "Copyright © 2010, MetaQuotes Software Corp."
#property link      "http://www.metaquotes.net"

#property indicator_chart_window
#property indicator_buffers 3
#property indicator_color1 Blue
#property indicator_color2 Red
#property indicator_color3 Yellow

extern int iHistory = 100;                            //Bars to use
extern double MA_Period_1 = 50;                       //Fast MA
extern double MA_Period_2 = 200;                      //Slow MA

double Line_0[], Line_1[], Arrow[];                            

//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int init()
  {
   
  SetIndexBuffer(0,Line_0);                  
  SetIndexBuffer(1,Line_1);
  
  SetIndexBuffer(1, Arrow);
   SetIndexStyle(1,DRAW_ARROW,EMPTY,3,Yellow);
   SetIndexArrow(1, 251);
   SetIndexEmptyValue(1,0.0);
  

   return(0);
  }

//+------------------------------------------------------------------+
//| Custom indicator iteration function                              |
//+------------------------------------------------------------------+
int start()
  {
  
   DrawMA();                                          //Draw MA function
   ErrorCheck();                                      //Check for errors
                
   return(0);
  }
  
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function                       |
//+------------------------------------------------------------------+
int deinit()
  {
  
   DeleteObjects();                                   //Delete objects on close

   return(0);
  }
    
//+------------------------------------------------------------------+


   void DeleteObjects()
     {
      for (int i=iHistory; i>=0; i--)
         {
          if (ObjectFind("signal" + i) != -1)
            {
             ObjectDelete("signal" + i);
            }     
         }
      }
   
//-------------------------------------------------------------------

   void DrawMA()
      {
       int    i, counted_bars;
   
      counted_bars = IndicatorCounted();
      i=Bars-counted_bars-1;
      if(i>iHistory) i = iHistory;
   
      double MA_1, MA_2, x1, x2, y1, y2;
   
      while(i>=0)
         {
       
          //Print("Checking bar ",i);
          MA_1=iMA(0,0,MA_Period_1,0,MODE_LWMA,PRICE_TYPICAL,i);             //MA 1
            //Print("MA_1 = ",MA_1," @ bar: ",i);
          Line_0[i]=MA_1;
       
          MA_2=iMA(0,0,MA_Period_2,0,MODE_LWMA,PRICE_TYPICAL,i);             //MA 2
          Line_1[i]=MA_2;
            //Print("MA_2 = ",MA_2," @ bar: ",i);
       
          x1=Line_0[i+1];                                                    //MA 1 - previous bar 
          x2=Line_0[i];                                                      //MA 1 - current bar 
          y1=Line_1[i+1];                                                    //MA 2 - previous bar 
          y2=Line_1[i];                                                      //MA 2 - current bar 
       
          if ((x1>y1 && x2<y2) || (x1<y1 && x2>y2))                          //if there was a crossover
           {
            
            Print("Crossover at bar ", i); 
            Arrow[i]=Line_0[i];
           }
       
          i--;
         }
      }

//----------------------------------------------------------------

   void ErrorCheck()
      {
       int err = GetLastError();
       if(err != 0)
         Alert("Error: ",err);
      }
 
if ((x1>y1 && x2<y2) || (x1<y1 && x2>y2)) { //if there was a crossover
    Print("Crossover at bar ", i); 
    Arrow[i]=Line_0[i];
} else Arrow[i] = EMPTY_VALUE;
Reason: