尾数的最左边的位总是 1 吗?

Is the leftmost bit of the mantissa always 1?

我正在看《程序的秘密生活》这本书。在第一章中,解释了数字设备公司 (DEC) 发明的一种允许双倍精度的技巧:“丢弃尾数的最左边的位会使精度加倍,因为我们知道它永远是 1,这使得还有一点空间。“

我看不懂。例如:让我们考虑一个 4 位浮点表示,其中包含 2 位尾数和 2 位指数。二进制数 01.11 代表 4.0。最左边的位是 0 而不是 1。

谁能给我解释一下,“丢弃最左边的位”和“精度加倍”是什么意思?

Floating-point 格式不同,但在大多数情况下,floating-point 表示是 sbef,其中s为+1或-1表示一个符号,b是一个基数(通常是2或10),e是一个指数, f 是以 b 为基数的 p 位数字。 bp是由格式决定的固定数字。 sef 根据所表示的数字而变化。 f 称为尾数。 (这是 floating-point 数的小数部分的首选术语。“尾数”是对数小数部分的历史术语。)

e 的边界以及 f 的缩放方式由格式决定。有时 f 被指定为在其第一位数字后有小数点(小数点的一般形式),因此其形式为 d0.d−1d− 2d1−p,其中每个 d i 是一个基数-b 数字(从 0 到 b−1,包括)。在这种形式下,0 ≤ f < b。 (我们不需要关心这个答案中的其他形式。)

在大多数情况下,f 的第一位不需要为零。如果它是零,我们可以将其删除并将其他数字左移一位。这会将 f 乘以 b,但我们可以通过将指数 e 减一来进行补偿。例如,如果 floating-point 数字是 0.1112•27,我们可以将其表示为 1.110 2•26。这为 f 末尾的新数字开辟了空间,与第一位数字为零相比,这为我们提供了更高的精度。

因此,我们希望第一个数字是 non-zero。这称为正常形式。第一个数字为零的数字是非规范化的。在可表示数字的最“底”端,e 达到了它的界限,我们不能进一步减少它,所以我们不能移动 f[=93 的数字=] 左边,我们必须在第一个位置留下一个零。这些必须非正规化的数字是次正规数。一些 floating-point 格式支持它们。有些没有。

当基数为二时,只有两个可能的数字值(0 和 1),因此,如果第一位不为零,则必须为一。因此,当我们使用以二为底且数字是范式时,我们知道它的第一个数字是一。因此,如果我们知道这个数字是正常的,就没有必要把这个数字和其他数字一起记录。

在IEEE-754格式中,记录指数的位也记录了这个数是否正常。上面的数字 sef 存储在我们可能称为 SEF。但是,它们并不直接作为二进制整数存储在这些位中。在指数字段 E 中,如果位全为零,则表示次正规数。这告诉我们指数 e 处于最低值,尾数的第一位为零。如果位都是 1,则表示该项是无穷大或 NaN。 e 在全零和全一之间的所有值表示 e 的值,并且尾数的第一个数字是 1。 (E的值不直接是e的值;有一个偏差用来调整,所以e = Ebias。例如,IEEE-754 binary32 的偏置为 127,因此 E of 00000001 表示 e = 1 − 127 = −126.)

因此,说我们“丢弃”了有效数的最左边的位是不正确的。实际发生的是最左边的位被编码在指数字段中,最右边的位存储在尾数字段中。

说这样处理最左边的位“精度加倍”也是草率的。的确,具有 p 位而不是 p−1 位的有效数具有两倍的可能值,因为每一位使值的数量加倍可代表的。因此,通过指数字段编码一位给我们的可能值是我们必须仅使用字段 F 作为尾数的两倍。但将其描述为精度提高一倍而不是精度提高一倍更清楚。