Why can't static const float members be initialized in a class?

Started by
27 comments, last by SiCrane 12 years, 1 month ago
I'm looking at the C++11 standard's section on constexpr right now and it says that it's implementation defined whether or not a compile time floating point computation yields the same result as a runtime computation. In other words, the thing you're saying makes constexpr possible but static const float impossible doesn't exist.
Advertisement
I used run-time floats as an example of how lax the standards are on how floating-point values are computed in general. Not that run-time values need to match compile-time values. That would imply that multiple floating-point modes would be forbidden under the new guidelines.

I never implied this. My second post was directed specifically at compile-time values. Basically you can’t have different compilers generating different values for the same thing. It just won’t work.
As long as compilers are required to translate the floats in a defined and consistent way, they can be compile-time constants. Otherwise they cannot. It is that simple.

Also, they are not required to match run-time derivations. That is float fVal = (2.0f/3.0f) on the compiler may not match the run-time value if truncation is involved.
However a run-time copy of the compiler-generated value is guaranteed to be a match for the compile-time value.

All of this makes sense. You can’t guarantee stability without these guarantees, and that is what the extensions and the new keywords provide.
The only thing that has been missing is a strict and standardized definition for what value the compiler will create when making these constants.

Think about it. What happens if a run-time float copies a compiler-generated const float, but that value is just ever so slightly different from what the compiler for that original library (containing the original float constant)? My compiler truncated. Theirs rounded up. Now my comparison of (mine >= theirs) returns false instead of true.


L. Spiro


[EDIT]
Drunken parts removed.
[/EDIT]

I restore Nintendo 64 video-game OST’s into HD! https://www.youtube.com/channel/UCCtX_wedtZ5BoyQBXEhnVZw/playlists?view=1&sort=lad&flow=grid


The only thing that has been missing is a strict and standardized definition for what value the compiler will create when making these constants.

Which doesn't exist in the current standard. It even says the exact opposite, that the standard "imposes no restrictions on the accuracy of floating-point operations" (Section 5.19).

You need to trust me
[/quote]
No, I don't. What was asked was the reason that the standards committee forbade inline definitions for static const floats in the previous standard. Not your supposition why they forbade it. If you can't cite an actual source then there is no reason to trust you, especially as your answer is in contradiction with what the standard actually says.
You guys need to read "The Design and Evolution of the C++ Programming Language" by B. Stroustrup. It is enlightening. It addresses this topic with a definitive answer.

Stephen M. Webb
Professional Free Software Developer

Random question: if static const float wasn't allowed because of possible inconsistencies, why is stuff like this allowed?
x = x + 93.01f;
That 93.01 could change depending on the compiler, or even the settings passed to it, and the result of the calculation can completely change depending on the processor flags (i.e. how rounding is done, etc.). So, why would this be OK, but not a named constant?

Think about it. What happens if a run-time float copies a compiler-generated const float, but that value is just ever so slightly different from what the compiler for that original library (containing the original float constant)? My compiler truncated. Theirs rounded up. Now my comparison of (mine >= theirs) returns false instead of true.

This would be affected for all the same reasons I mentioned above.
Don't pay much attention to "the hedgehog" in my nick, it's just because "Sik" was already taken =/ By the way, Sik is pronounced like seek, not like sick.

You guys need to read "The Design and Evolution of the C++ Programming Language" by B. Stroustrup. It is enlightening. It addresses this topic with a definitive answer.

Which is?
The storage conversion rules for floating-point types, including rounding behavior, is defined in IEEE-754.
Float's are always stored in the same format on all machines, even in the same endianness.
I see no technical reason why floats cannot be initialized inline just like integral type. It is, after-all, merely an illusion that floating-point types are not integral values.

I would presume the reason they limited it to integral types is to ease the burden of implementation on compiler vendors.
- The trade-off between price and quality does not exist in Japan. Rather, the idea that high quality brings on cost reduction is widely accepted.-- Tajima & Matsubara

The storage conversion rules for floating-point types, including rounding behavior, is defined in IEEE-754.

That's a standard, but neither the C or C++ standard mandates IEEE-754 for floating point types, as far as I'm aware. You can check on any given C++ implementation with std::numeric_limits<float>::is_iec559, for example.


Float's are always stored in the same format on all machines, even in the same endianness.
[/quote]
That's not true. In fact I get the impression that it's why IEE754 came about in the first place! Wikipedia has some exceptions.

...even in the same endianness.

Actually that's not right either. IEEE-754 doesn't specify byte order, though float endianness generally follow integer endianness. However, machines with big endian integers can store floats little endian and vice versa. It's one of the minor headaches you need to deal with when writing truly universal binary serialization (which is part of the reason that so many cross platform exchange formats punt and encode floats as text). See Wikipedia's entry on endianess.

This topic is closed to new replies.

Advertisement