Can a c++ compiler implement floating-point numbers using projective infinity?

141 Views Asked by At

This question is inspired by this question about negative infinity and this other question about the total ordering of floating point numbers.

It is motivated by my impression that, given some judicous lawyering, -std::numeric_limits<float>::infinity() is guaranteed to be valid whenever std::numeric_limits<float>::has_infinity, regardless of whether std::numeric_limits<float>::is_iec559 is true or not.

But before I post an answer to the negative infinity question supporting that, I need to get past a side issue: Whether you can implement float with (negative) infinity in a way that infinity == -infinity (the way it works in a projective space) and still be compliant and useful.

Now, -infinity would not be useful if it were not less than all other floating point values. But then, if infinity == -infinity, this value has to be simultaneously greater and less than all the other floating-point values. This breaks the strict total ordering we expect from real numbers (comparison can't be transitive across infinity or else it's useless), but as the question about total ordering shows, floating-point numbers already deviate from strict total ordering because of NaN, and they're still considered totally ordered.

Is there anything in the Standard the prevents the implementation of a meaningful -std::numeric_limits<float>::infinity() when also -std::numeric_limits<float>::infinity() == std::numeric_limits<float>::infinity() ?

Needless to say, this would NOT be an implementation that uses IEEE754/IEC559 for floating point. Big chunks of the Standard go out the window in implementations that don't use IEEE754/IEC559. But given that such implementations are rarer than hen's teeth, we need to stick to language-lawyering rather than what existing compilers do, what we think is logical, or what we would prefer to see.

1

There are 1 best solutions below

0
F.v.S. On

It seems to me that such an implementation is allowed. On such an implementation, inf may need to be specially treated as NaN except that it should compare equal to itself. It's unclear to me what should std::strong_order/std::weak_order return when either argument is projective inf, but I believe implementation are allowed to make decisions at their own will (N4868 [cmp.alg]/1.3, N4868 [cmp.alg]/2.3).

The only possible blocker to me is a note in N4868 [alg.clamp]/4, which is, IIUC, not strict as it's non-normative:

[Note 1: If NaN is avoided, T can be a floating-point type. — end note]

When projective infinity is allowed for FP types, the note doesn't seem correct, as projective inf also needs to be avoided.