Reputation: 109
I am dealing with floating point very small in magnitude and would like to round to 0
whenever the floating point cannot be represented by a double
because it is too small in magnitude.
This code:
#include <iostream>
#include <cmath>
int main() {
double x{100.0};
double y{(-1.0) * 1.7976931348623157e308};
double z{std::pow(x, y)};
std::cout << typeid(z).name() << ": " << z << std::endl;
std::cout << (z == 0) << std::endl;
return 0;
}
prints
$ ./a.out
d: 0
1
for me (clang version 11.0.0, -std=c++11), as desired.
Question:
Do expressions that result in a floating point too small in magnitude to be represented by a double
always evaluate to 0
when assigned to a double
? (including for other C++ compilers?) If not, how
can I achieve this behavior, or test for such an expression being too small in magnitude?
Edit:
As @Eljay pointed out, I could test if the expression results in a denormalized double
.
The solution then would be to test std::fpclassify(z) == FE_SUBNORMAL
and if so to set z
equal to zero. This solves my problem.
I should point out that in my question I asked for setting z
equal to zero when the expression assigned to it is not representable as double
due to floating point underflow. A double
that classifies as FE_SUBNORMAL
is representable by a double
, so technically the answer by @eerorika is correct.
Upvotes: 1
Views: 437
Reputation: 238401
Do expressions that result in a floating point too small in magnitude to be represented by a double always evaluate to 0
Not necessarily. The result depends on the rounding mode. For example, if FE_UPWARD
is used, then you would get a very small non-zero result - assuming rounding modes are supported by the language implementation.
If not, how can I achieve this behavior
FE_TOWARDZERO
rounding mode should behave like that - again, assuming rounding modes are supported.
Upvotes: 1