Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How are Inf and NaN implemented?

As mathematical concepts, I am well aware of what inf and nan actually are. But what I am really interested in is how they are implemented in programming languages.

In python, I can use inf and nan in arithmetic and conditional expressions, like this:

>>> nan = float('nan')
>>> inf = float('inf')
>>> 1 + inf
inf
>>> inf + inf
inf
>>> inf - inf
nan

This would lead me to believe that python internally has a special reserved bit sequence for these two mathematical quantities, and no other number can assume these positions. Is my assumption correct? Can you please enlighten me in this regard?

If my assumption is correct, then this can be explained easily:

>>> inf == inf
True

However, this is not:

>>> nan == nan
False

Obviously, in mathematics, this is the right answer. But how does python know that it should spit out False in this instance?

Furthermore, how does python's implementation differ from that of java or c++?

like image 725
cs95 Avatar asked Jul 01 '17 19:07

cs95


People also ask

What are NaN and INF values?

inf is infinity - a value that is greater than any other value. -inf is therefore smaller than any other value. nan stands for Not A Number, and this is not equal to 0 .

How do you create a NaN?

It is generated when a floating point number is divided by zero or if the square root of a negative number is computed. For example, have a look at the following snippet. In the snippet above, you can observe that NaN is produced as a result of 3 simple operations: Dividing a float / double zero with zero.

How is NaN represented?

Binary format NaNs are represented with the exponential field filled with ones (like infinity values), and some non-zero number in the significand field (to make them distinct from infinity values).

What causes NaN in C?

NaN, an acronym for Not a Number is an exception that usually occurs in the cases when an expression results in a number that is undefined or can't be represented. It is used for floating-point operations. For example: The square root of negative numbers.


2 Answers

Typically, the floating point arithmetic is implemented directly by hardware. There are indeed special bit patterns for infinity and NaN, which are recognized by the hardware floating-point unit.

IEEE 64-bit floating-point numbers, the kind used in CPython on typical systems, have 1 bit for the sign, 11 bits for the exponent, and 52 bits for the mantissa. See https://en.wikipedia.org/wiki/Double-precision_floating-point_format

If the exponent contains 0b11111111111 (all ones), then the number is either inf or nan, depending on what is stored in the mantissa. Python does not need to do anything special to handle these cases. You will get the same results whether you compare the numbers in Python, C, Java, or assembly language.

like image 68
Dietrich Epp Avatar answered Oct 04 '22 06:10

Dietrich Epp


Those are not python-specific behavior, it's rather the floating-point standard Python use (and possibly all common languages?).

nan and inf are special value of the IEEE_754 floating point standard. They have internal representations (the bit sequence you mention) of course, but their behavior is not usual. The behavior is not usual wrt other floats values, but it is well defined by IEEE_754. Implementation is handled at instruction level. (The processor handle this in its floating-point unit circuitry)

One specified and not trivial behavior, NaN != everything, including itself.

Knowing that, you can write something like:

def isNaN(f): return f != f
like image 37
johan d Avatar answered Oct 04 '22 07:10

johan d