Does "epsilon" really guarantees anything in floating-point computations?!
- by Michal Czardybon
To make the problem short let's say I want to compute expression: a / (b - c) on float's.
To make sure the result is meaningful, I can check if 'b' and 'c' are inequal:
float eps = std::numeric_limits<float>::epsilon();
if ((b - c) > EPS || (c - b) > EPS)
{
return a / (b - c);
}
but my tests show it is not enough to guarantee either meaningful results nor not failing to provide a result if it is possible.
Case 1:
a = 1.0f;
b = 0.00000003f;
c = 0.00000002f;
Result: The if condition is NOT met, but the expression would produce a correct result 100000008 (as for the floats' precision).
Case 2:
a = 1e33f;
b = 0.000003;
c = 0.000002;
Result: The if condition is met, but the expression produces not a meaningful result +1.#INF00.
I found it much more reliable to check the result, not the arguments:
const float INF = numeric_limits<float>::infinity();
float x = a / (b - c);
if (-INF < x && x < INF)
{
return x;
}
But what for is the epsilon then and why is everyone saying epsilon is good to use?