Reputation: 1584
Run the the following C++ program twice. Once with the given destructor and once with std::fesetround(value);
removed from the destructor. Why do I receive different outputs? Shouldn't destructor be called after function add
? I ran both versions on http://cpp.sh/ and Clang++ 6.0, and g++ 7.2.0. For g++, I also included #pragma STDC FENV_ACCESS on
in the source code, nothing changed.
#include <iostream>
#include <string>
#include <cfenv>
struct raii_feround {
raii_feround() : value(std::fegetround()) { }
~raii_feround() { std::fesetround(value); }
inline void round_up () const noexcept { std::fesetround(FE_UPWARD ); }
inline void round_down() const noexcept { std::fesetround(FE_DOWNWARD); }
template<typename T>
T add(T fst, T snd) const noexcept { return fst + snd; }
private:
int value; };
float a = 1.1;
float b = 1.2;
float c = 0;
float d = 0;
int main() {
{
raii_feround raii;
raii.round_up();
c = raii.add(a, b);
}
{
raii_feround raii;
raii.round_down();
d = raii.add(a, b);
}
std::cout << c << "\n"; // Output is: 2.3
std::cout << d << "\n"; // Output is: 2.3 or 2.29999
}
Upvotes: 0
Views: 367
Reputation: 1584
All I needed to do was to do std::cout << std::setprecision(30);
before calling std::cout
in the code (iomanip
should be included as well).
Upvotes: 0
Reputation: 222900
Using the floating-point environment facilities requires inserting #pragma STDC FENV_ACCESS on
into the source (or ensure that they default to on
for the implementation you are using. (Although STDC
is a C feature, the C++ standard says that these facilities are imported into C++ by the <cfenv>
header.)
Doing so at cpp.sh results in “warning: ignoring #pragma STDC FENV_ACCESS [-Wunknown-pragmas]”.
Therefore, accessing and modifying the floating-point environment is not supported by the compiler at cpp.sh.
Upvotes: 1