Pynote

Python、機械学習、画像処理について

浮動小数点数について

浮動小数点数

浮動小数点数 (floating point numbers) は、固定長の仮数部と指数部を持つ、実数の近似表現法である。

\displaystyle
\text{significand} \times base^{\text{exponent}}

IEEE754

正式名称は IEEE Standard for Binary Floating-Point Arithmetic である。
この規格では2進浮動小数点数を以下のように表現する。

\displaystyle
\pm f \times 2^e

f は有効数字を構成する部分で、仮数という。
このままでは、(1.00)_2 \times 2^0 = (0.10)_2 \times 2^1 = (0.01)_2 \times 2^2 のようにある数値に対して、複数の表現方法が存在するので、仮数の整数部は1にすると約束することで、浮動小数点表現を一意にする。
この取り決めに従う浮動小数点数正規化浮動小数点数という。

符号化方法

浮動小数点数は符号部、指数部、仮数部の3つの要素によって特徴付けられるビット列で符号化する。

\displaystyle
\begin{array}{|c|c|c|}
\hline
符号部 & 符号付指数部 & 仮数部  \\
\hline
s & e_1 e_2 \cdots e_q & f_1 f_2 \cdots f_p  \\
\hline
1ビット & qビット & pビット  \\
\hline
\end{array}

符号部

0で正、1で負を表す。

仮数部 (mantissa / significand / fraction)

仮数 ff = (1.b_1 b_2 \cdots b_p)_2, b_i = 0, 1 という p + 1 桁のビット列で表す。
正規化浮動小数点数では先頭ビットは必ず1なので、データ上は p ビットで表す。
このことをけち表現という。

指数部 (signed exponent / biased exponent)

冪指数 e は負の値もとり得るが、e + bias のように値にある定数 bias を加算して非負の整数で表現する。
このことをバイアス表現または下駄履き表現という。

例えば倍精度の場合、値 e を表現する場合、e + 1023 という値で表す。

\displaystyle
\begin{array}{|c|c|c|}
\hline
実際の値 & -1022 & -1021 & \cdots & 1022  & 1023 \\ \hline
バイアス表現 & 1 & 2 & \cdots & 2045  & 2046 \\ \hline
\end{array}

冪指数 e の最小値、最大値をそれぞれ e_{min}, e_{max} とすると、

\displaystyle
\begin{array}{|c|c|c|}
\hline
バイアス表現 & 意味 \\
\hline
(00 \cdots 0)_2 - bias & 特殊な値を表すのに使用 \\
\hline
(00 \cdots 1)_2 - bias & e_{min} \\
\hline
\vdots & \vdots \\
\hline
(11 \cdots 10)_2 - bias & e_{max} \\
\hline
(11 \cdots 1)_2 - bias & 特殊な値を表すのに使用 \\
\hline
\end{array}

であるから、

\displaystyle
e_{min} = 1 - bias \\
e_{max} = (2^q - 1) - 1 - bias = 2^q - 2 - bias

となる。

ビット列が表す浮動小数点数

\displaystyle
\begin{array}{|c|c|c|}
\hline
符号部 & 符号付指数部 & 仮数部  \\
\hline
s & e_1 e_2 \cdots e_q & f_1 f_2 \cdots f_p  \\
\hline
1ビット & qビット & pビット  \\
\hline
\end{array}

このビット列で表される浮動小数点数は次のようになる。

\displaystyle
x = (-1)^s \times (1.f_1 f_2 \cdots f_p)_2 \times 2^{(e_1 e_2 \cdots e_q)_2 - bias}

正規化浮動小数点数の範囲

正規化浮動小数点数の0に最も近い値を N_{min}、0から最も遠い値を N_{max} とすると、

\displaystyle
N_{min} = (1.00\cdots0)_2 \times 2^{e_{min}} = 2^{e_{min}} \\
N_{max} = (1.11 \cdots 1)_2 \times 2^{e_{max}} = (2 - 2^{-p}) \times 2^{e_{max}} = 2^{e_{max}} - 2^{e_{max} \ \ - p}

となる。


特殊な数について

e + bias の値が (00 \cdots 0)_2 = 0 及び (11 \cdots 1)_2 = 2^q - 1 の場合は、以下の特殊な値を表すために予約されている。

\displaystyle
\begin{array}{|c|c|c|}
\hline
種類 & 符号部 & 指数部 & 仮数部 \\
\hline
零 & s = 0, 1 & e + bias = (00 \cdots 0) & f = (00 \cdots 0)_2 \\
\hline
非正規化数 & s = 0, 1 & e + bias = (00\cdots0)_2 & f \ne (00\cdots0)_2 \\
\hline
無限 & s = 0, 1 & e + bias = (11\cdots1)_2 & f = (00\cdots0)_2 \\
\hline
NaN & s = 0, 1 & e + bias = (11\cdots1)_2 & f \ne (00\cdots0)_2 \\
\hline
\end{array}

零 (zero)

符号付きで \pm 0 を表す。

非正規化数 (denormalized number (旧称) / subnormal number)

正規化浮動小数点数の0とそれに最も近い値 \pm N_{min} = 2^{e_{min}} は間隔が空いてしまっている。
そのため、(0.f_1 f_2 \cdots f_p)_2 \times 2^{e_{min}} という形式で表す浮動小数点数|x| < N_{min} に作る。
先頭ビットが1でないので、これを非正規化数という。
このとき有効桁数が正規化浮動小数点数と比較して1桁少ないことに注意する。
非正規化数は間隔が \pm (0.00 \cdots 01)_2 \times 2^{e_{min}}固定小数点数である。

無限 (infinity)

符号付きで \pm \infty を表す。
無限は演算の結果、正規化浮動小数点数で表せる範囲を超えてしまった場合に生成される数である。

NaN (Not a Number)

NaN は 0 / 0\sqrt{-1} など定義されない演算結果として生成される特殊な数である。

計算機イプシロン/マシンイプシロン (machine epsilon)

計算機イプシロン11 より大きい最小の浮動小数点数との距離である。
(1.00 \cdots 0)_2 \times 2^0 の次に大きい値は、(1.00 \cdots 1)_2 \times 2^0 であるから、その差は \varepsilon = 2^{-p} である。

単精度/倍精度

IEEE754 では32ビットで表す単精度及び64ビットで表す倍精度が規定されている。
符号化した際の各ビット数は以下のようになる。

\displaystyle
\begin{array}{|c|c|c|}
\hline
 & 単精度 & 倍精度 \\
\hline
符号部のビット数 & 1 & 1 \\
\hline
仮数部のビット数 p & 23 & 52 \\
\hline
指数部のビット数 q & 8 & 11 \\
\hline
全体のビット数 1 + p + q & 32 & 64 \\
\hline
バイアス bias & 127 & 1023 \\
\hline
\end{array}

\displaystyle
\begin{array}{|c|c|c|}
\hline
 & 単精度 & 倍精度 \\
\hline
e_{min} & -126 & -1022 \\
\hline
e_{max} & 127 & 1023 \\
\hline
N_{min} & 2^{-126} \approx 1.18 \times 10^{-38} & 2^{-1022} \approx 2.23 \times 10^{-308} \\
\hline
N_{max} & 2^{128} - 2^{104} \approx 3.40 \times 10^{38} & 2^{1024} - 2^{971} \approx 1.80 \times 10^{308} \\
\hline
\varepsilon & 2^{-23} \approx 1.19 \times 10^{-7} & 2^{-52} \approx 2.22 \times 10^{-16} \\
\hline
非正規化数の間隔 & 2^{-149} \approx 1.40 \times 10^{-45} & 2^{-1074} \approx 5.00 \times 10^{-324} \\
\hline
\end{array}