From MetaSharp
Article Author(s): Audric Thevenet
All Rights Reserved.
definition of the double type
The following code is the best way I could come up with to work correctly with doubles. The float version is not provided yet, but after reading a bit the code, you should manage to easily extend it to floats. The most important functions here are:
- GetExpoBase2() extracts the base2 exponent from the double (putting aside the sign bit and the mantissa)
- Equals() gets the exponents (e1,e2) of both doubles (d1,d2) and the exponent (e3) of their difference (d1-d2), then the 2 doubles (d1,d2) are considered being equal only if their difference is close enough to 0. This is done comparing the exponents. Example: e3=-50 (meaning 2^-50) e1=-1 e2=-1 then e3-e2=-49 and e3-e1=-49 both less than -48. It means that e1 and e2 are equal because their difference significant bits are located 2^48 lower... hard to tell if it's clear enough, I'll edit later if I come up with a clearer explaination ^^
Download Double comparison Sample for VC2005
compare.cpp
// compare.cpp
#include "compare.h"
namespace metasharp
{
inline int GetExpoBase2(double d)
{
int i = 0;
((short *)(&i))[0] = (((short *)(&d))[3] & (short)32752); // _123456789ab____ & 0111111111110000
return (i >> 4) - 1023;
}
bool Equals(double d1, double d2)
{
if (d1 == d2)
return true;
int e1 = GetExpoBase2(d1);
int e2 = GetExpoBase2(d2);
int e3 = GetExpoBase2(d1 - d2);
if ((e3 - e2 < -48) && (e3 - e1 < -48))
return true;
return false;
}
int Compare(double d1, double d2)
{
if (Equals(d1, d2) == true)
return 0;
if (d1 > d2)
return 1;
return -1;
}
bool Greater(double d1, double d2)
{
if (Equals(d1, d2) == true)
return false;
if (d1 > d2)
return true;
return false;
}
bool GreaterOrEqual(double d1, double d2)
{
if (Equals(d1, d2) == true)
return true;
if (d1 > d2)
return true;
return false;
}
bool Less(double d1, double d2)
{
if (Equals(d1, d2) == true)
return false;
if (d1 < d2)
return true;
return false;
}
bool LessOrEqual(double d1, double d2)
{
if (Equals(d1, d2) == true)
return true;
if (d1 < d2)
return true;
return false;
}
}
compare.h
// compare.h
#ifndef COMPARE_H
#define COMPARE_H
namespace metasharp
{
int Compare(double d1, double d2);
bool Equals(double d1, double d2);
bool Greater(double d1, double d2);
bool GreaterOrEqual(double d1, double d2);
bool Less(double d1, double d2);
bool LessOrEqual(double d1, double d2);
}
#endif