IEEE 754, двоичные числа 32 указаны следующим образом:
![IEEE 754, binary-32 number format](https://upload.wikimedia.org/wikipedia/commons/d/d2/Float_example.svg)
По существу, оно состоит из трех частей:
- 1 бит
float32_sign
представляющий знак - 23 бит
float32_fraction[]
, представляющий коэффициенты двоичной дроби - 8 бит
float32_exp
, представляющий целое число 2
См. Википедия/ Single-precision_floating-point_format для деталей.
Формула для получения действительного числа:
![IEEE 754, binary-32 number formula](https://i.stack.imgur.com/OgLzh.gif)
Забывая показатель степени, дробная часть можетточно представлять pow(2, 23) = 8388608
значений.Максимальные и минимальные значения в этом диапазоне:
( 1 + 0, 1 + sum(pow(2, -i)) ) # All co-efficients being 0 and 1 resp. in the above formula
=> ( 1, 2 - pow(2, -23) ) # By geometric progression
~> ( 1, 2 ) # Approximation by upper-bound
Таким образом, для показателя степени 1 (float32_exp = 128
) у нас будет 8388608 чисел между (1,2)
и (-1,-2)
.
Однако для больших чисел, например, когда показатель степени равен 126 (float32_exp = 253
), у нас все еще есть только 8388608 чисел, представляющих разрыв между (2^126), 2^127)
и (-2^126, -2^127)
.
График распределения между 1 и 128 выглядит следующим образом:
![enter image description here](https://i.stack.imgur.com/vqNeB.png)
График настолько крутой при 0, что при построении графика он будет выглядеть как единственное значение только при 0.Обратите внимание, что затухание является экспоненциальным.
Формула для получения числа чисел с плавающей запятой между двумя значениями:
def num_floats(begin, end):
# pow(2, 23) * (log(end, 2) - log(start, 2)) == pow(2, 23) * log(end/start, 2)
return 8388608 * math.log(float(end)/float(begin), 2)