浮動小数点数の比較回路のつくり方
浮動小数点数は以下のような内部構造を持つ。
符号部(1ビット)
指数部(8ビット)
仮数部(23ビット)
符号部、指数部、仮数部を順番に比較することで浮動小数点数の大小の比較ができる。
符号部の比較
符号部の値が異なる場合、0の方が正の値なので大きい
符号が同じ場合は指数部の比較へ進む
指数部の比較
指数部の値が異なる場合、指数部の値が大きい方が大きい
指数部の値が同じ場合は仮数部の比較へ進む
仮数部の比較
仮数部の値が異なる場合、仮数部の値が大きい方が大きい
仮数部の値が同じ場合、ふたつの浮動小数点数は「同値」
⚠️ (仮数部のそれぞれのビットは 1/2, 1/4, 1/8, 1/16, ... を表すが、大きさを比較する場合はビット列をそのまま比較するだけで良い)
ゼロ・非正規数・無限大・NaN
上の比較ロジックに加えて、以下の特殊な値についても考慮する必要があるかも。
ゼロ
指数部 == 0
仮数部 == 0
⚠️(正のゼロと負のゼロがある)
非正規数(Float::MIN)
指数部 == 0
仮数部 != 0
⚠️(浮動小数点数で表現不可能なくらい小さい数値)
無限大(Float::INFINITY)
指数部 == 255
仮数部 == 0
⚠️(正の無限大と負の無限大がある)
NaN
指数部 == 255
仮数部 != 0
⚠️ (非数/JavaScriptに倣って、NaNと比較演算はすべて false を返すことにする)
メモ
正のゼロと負のゼロ
符号部の比較でいい感じに判定されそう
正の無限大と負の無限大
符号部の比較でいい感じに判定されそう