WHRoeder: this code good (especially check "added" and "default")? It may also serve as an easy final-reference for those who visit this thread and just go the last page (as I did)
#define LT 0#define GT 1#define GTE 2#define LTE 3#define EQ 4#define NEQ 5bool doublecomp(double a,int type,double b){
// See https://forum.mql4.com/45053/page4// 0 compare doesn't need this functionswitch(type){
case LT: return(b-a>Point/2.);
case GT: return(a-b>Point/2.);
case GTE: return(a-b>-Point); // Addedcase LTE: return(b-a>-Point); // Addedcase EQ: return(!(MathAbs(a-b)>Point/2.));
case NEQ: return(MathAbs(a-b)>Point/2.);
default: return(-1); // Added - needed to avoid compile error about not all control paths returning a value
}
}
SDC: How can if( !MathAbs( a - b ) > Point/2) be used to compare for equality? That would tell you 1.4999 == 1.5000
It doesn't
if( ! (MathAbs( a - b ) > Point/2) ) be used to compare for equality? That would tell you 1.4999 == 1.5000 if( ! (MathAbs(1.4999 - 1.5000 > 0.00005 ) if( ! (0.0001 > 0.00005 ) if( ! (true ) if( false ) 1.4999 is NOT equal to 1.5000
And I had pointed out to Roel13 in a PM that the GEQ/LEQ must be -Point/2 but he didn't edit the post
And as I previous posted, you only have to worry about such nonsense if the equality/non-equality is important. If you want to open above the high of a candle, does it matter if (because of rounding) that it might trigger at exactly the high? If no just use bid > high[].
#define LT 0#define GT 1#define GTE 2#define LTE 3#define EQ 4#define NEQ 5bool ComparePrice(double a,int type,double b){
// See https://forum.mql4.com/45053/page4// 0 compare doesn't need this functionswitch(type){
case LT: return(b-a>Point/2.);
case GT: return(a-b>Point/2.);
case GTE: return(a-b>-Point/2.);
case LTE: return(b-a>-Point/2.);
case EQ: return(!(MathAbs(a-b)>Point/2.));
case NEQ: return(MathAbs(a-b)>Point/2.);
}
return(-1);
}
And, maybe a secondary function for comparing all other doubles that are not prices...
bool CompareNormal(double a,int type,double b){
// With thanks https://forum.mql4.com/45053/page4// 0 compare doesn't need this functionswitch(type){
case LT: return(b-a>0.0000000000000000000000000000001);
case GT: return(a-b>0.0000000000000000000000000000001);
case LTE: return(b-a>-0.0000000000000000000000000000001);
case GTE: return(a-b>-0.0000000000000000000000000000001);
case EQ: return(!(MathAbs(a-b)>0.0000000000000000000000000000001));
case NEQ: return(MathAbs(a-b)>0.0000000000000000000000000000001);
}
return(-1);
}
See also 'MQL4 Reference > Language Basics > Data Types > Real Types (double, float)' in regards using small number for comparision.
Maybe someone knows how to write 0.00...1 better in expon
Noted that the value of epsilon in the above example can not be less than the predefined constant DBL_EPSILON. The value of this constant is 2.2204460492503131e-016.
Again, none of this is necessary, except in the case where the equals/not equals is important. E.g. open above the previous high, you don't want to open at the high due to round off.
I think this topic is dealt with too much unnecessary complexity.
Try to make your programmer's life always as easy as possible. Write defines (or go ahead with methods if you really must) in those classes where you need your double comparisons:
// add more floating point zeros if you need a higher precision
#define isZero(x) (fabs(x) < 0.000000001)
#define isEqual(x,y) (fabs(x-y) < 0.000000001)
When you need to compare two doubles then use it in a condition like this:
if (isEqual(myFirstDouble, mySecondDouble))
{
// first and second doubles are considered equal// do something
}
If you want to see if a double is zero (or very, very close to zero) use a condition like this:
if (isZero(myDouble))
{
// myDouble is considered zero// do something
}
On a side note, since I see many posts talking about divisions:
With encapsulation we tend to forget about the costs of code that is "outsourced" to some utility methods. Remind yourself that divisions are computationally very expensive! Especially, once wrapped in nice utility methods somewhere in utility classes, we start to use them everywhere in indicators or EAs and have long forgotten what computational steps they perform. When using the strategy tester we pay a lot of unnecessary time for our sloppiness.
Rule of thumb: Additions and subtractions are much much faster than multiplications and divisions. The division operation takes the highest computation time. Optimize divisions - wherever possible! If the denominator is fix like in this loop...
then replace the denominator x with its inverted value 1/x:
for(int i=0; i < rates_total; i++)
{
// ...double fraction = 0.01 * someNumeratorValue; // replace a denominator with it's inverted value, if possible.
// ...
}
Also, if the result of a division is always the same, then do the computation once and save the result in a variable so you can use it everywhere in your code (e.g. in loops):
double tradesPerDay = totalTradesPerYear/365;
for(int i=0; i < rates_total; i++)
{
// use precomputed tradesPerDay rather than computing the division here.
}
WHRoeder: this code good (especially check "added" and "default")? It may also serve as an easy final-reference for those who visit this thread and just go the last page (as I did)
That code is not accurate.
How can if( !MathAbs( a - b ) > Point/2) be used to compare for equality? That would tell you 1.4999 == 1.5000
if( ! (MathAbs(1.4999 - 1.5000 > 0.00005 )
if( ! (0.0001 > 0.00005 )
if( ! (true )
if( false ) 1.4999 is NOT equal to 1.5000
I use
or for doubles that arn't actual prices, a higher precision
Raptors post about this code
So if you use,
I have tested that method in a variety of ways I have not found a scenario where it would not return the expected or desired result.Final code... Thanks WHRoeder
And, maybe a secondary function for comparing all other doubles that are not prices...
See also 'MQL4 Reference > Language Basics > Data Types > Real Types (double, float)' in regards using small number for comparision.
Maybe someone knows how to write 0.00...1 better in expon
So there is something else interesting I found, potentially in connection with "// 0 compare doesn't need this function".
Maybe a bug only in the latest versions, not sure. Comparing with 0 no longer functions correctly. I had to resort to something unfriendly like;
outcome=(int(outcome*100)/100.0); // Resolution 2 digits
Just to ensure that 0 values actually ended up as 0 values.
WHRoeder, thanks. More study needed :)
I think this topic is dealt with too much unnecessary complexity.
Try to make your programmer's life always as easy as possible. Write defines (or go ahead with methods if you really must) in those classes where you need your double comparisons:
When you need to compare two doubles then use it in a condition like this:
If you want to see if a double is zero (or very, very close to zero) use a condition like this:
On a side note, since I see many posts talking about divisions:
With encapsulation we tend to forget about the costs of code that is "outsourced" to some utility methods. Remind yourself that divisions are computationally very expensive! Especially, once wrapped in nice utility methods somewhere in utility classes, we start to use them everywhere in indicators or EAs and have long forgotten what computational steps they perform. When using the strategy tester we pay a lot of unnecessary time for our sloppiness.
Rule of thumb: Additions and subtractions are much much faster than multiplications and divisions. The division operation takes the highest computation time. Optimize divisions - wherever possible! If the denominator is fix like in this loop...
then replace the denominator x with its inverted value 1/x:
Also, if the result of a division is always the same, then do the computation once and save the result in a variable so you can use it everywhere in your code (e.g. in loops):
Cheers,
A.T.