Why is division close to zero having different behaviors in python?

This is actually not a problem, more curious about floating point arithmetic in a Python implementation.

Can someone explain the following behavior?

>>> 1/1e-308 1e+308 >>> 1/1e-309 inf >>> 1/1e-323 inf >>> 1/1e-324 Traceback (most recent call last): File "<stdin>", line 1, in <module> ZeroDivisionError: float division by zero 

It seems that 1 divided by a number close to zero is inf and if it approaches a ZeroDivisionError . This seems like weird behavior.

The same output for python 2.x / 3.x.


EDIT : my main question is: why do we get inf for some range and not ZeroDivisionError , assuming python is considered null 1e-309

+5
source share
3 answers

This is due to the IEEE754 floating point format itself, and not to its Python implementation.

Generally speaking, floats can represent smaller negative numbers than larger positives due to denormal numbers . Here, part of the float mantissa is already implicitly supposed to start from 1, but rather describes the entire mantissa and begins with zeros. If you do not know what it is, I would advise you to read about how floats are represented, perhaps starting here .

Because of this, when you invert a denormal number, you may end up in a positive exponent too large to represent. Then the computer issues inf in its place. 1e-308 in your example is actually also denormal, but still not small for overflow when inverting (because among normal numbers, the standard actually allows for slightly more positive than negative indicators).

In the case of 1e-324 this number is simply too small to be represented even as denormal, so float literal is effectively zero. That is why you get division by zero. The smallest 64-bit float represented (just below) is 5e-324 .

+7
source

The smallest value that can be used as a floating point number in Python:

2.2250738585072014e-308

Python uses double precision floats, which can contain values ​​from 10 to -308 to 10 to a power of 308.

Wikipedia - double precision floating point format

In fact, you can probably get numbers less than 1e-308 through denormals , but there is significant success in this. I found that Python is able to handle 1e-324 , but overflows on 1e-325 and returns 0.0 as the value.

+4
source

Most of the things have already been explained to Dolda2000 in the answer. However, it would be helpful to see this.

 >>> 1e-308 1e-308 >>> 1e-309 1e-309 >>> 1e-323 1e-323 >>> 1e-324 0.0 

As you can see, 1e-324 is 0.0 in the python implementation. Like Dolda2000, it is very beautiful: this number is simply too small to be represented even as denormal, so float literal is effectively zero

+2
source

Source: https://habr.com/ru/post/1243013/


All Articles