为什么为NaN保留了这么多浮点/双精度值



这只是编程中困扰我的另一件事。

我的问题

因此,我已经在这个IEEE-754浮点转换器上玩了一段时间,我发现,当指数设置为其最大值时,尾数值为零将导致正或负的无穷大(取决于符号的设置),所有非零尾数值都将导致NaN(也称为非数字)。

然而,有这么多NaN值的具体原因吗?老实说,对我来说,这只是一种不必要的范围浪费。我明白为什么NaN存在,但它只是一个奇异值,我从未见过";不同种类的";CCD_ 3的任何位置。

我的想法

怎么样:如果指数和尾数都处于最大值,则将该值视为无穷大(正还是负仍然取决于符号)。这将消除NaN值,并且几乎是floatdouble类型的范围的两倍。

但现在,我们把NaN值放在哪里?在IEEE-754浮点类型中,还有一件事可以通过不同的值来实现:零。有CCD_ 6和CCD_。他们总是被以同样的方式对待,那么为什么不丢弃-0并将其视为NaN呢?当然,这需要处理器在出现0时总是删除符号,但我认为这对性能几乎没有影响。

我知道标准很可能不会很快改变,但这个系统不会更好有什么具体的原因吗?回到最初的问题:这么大的一大块值被认为是NaN有原因吗

NaN不是奇异值。

首先,在浮点数据的级别(IEEE 754-2008表3.1中的级别2),有两个NaN,一个安静的NaN和一个信令的NaN。这些也出现在浮点数据的表示级别(级别3)。

其次,根据IEEE 754-2008 6.2.1:,作为编码浮点数据(4级)的位串,有效位字段的第一位编码NaN是安静的(1)还是信令的(0),其余的位可以用于诊断信息(只要它们对于信令NaN不全为零,因为这将表示+∞)

编码时,所有NaN都有一个符号位和一个将编码识别为NaN所需的位模式,并确定其类型(sNaN与qNaN)。尾部有效位字段中的其余位对有效载荷进行编码,有效载荷可能是诊断信息(见上文)。

例如,可以将位设置为生成NaN(或其哈希)的指令的地址。或者,浮点对象数组可能被初始化为具有特定有效位的NaN,然后程序结果中的任何NaN都可以指示它们是来自该初始数据还是在执行过程中生成的。

我隐约记得IEEE-754委员会的一名成员对有效载荷领域有其他一些创造性的用途,但我不记得它是什么。

这很令人惊讶,不是吗?在IEEE-754单精度中,有16777214个不同的NaN值,并且在双精度中,不少于9007199254740990,或其中的9万亿。

这只是猜测,但我认为部分原因很简单:易于实施。IEEE-754浮点已经很难实现,特别是由于子规范的存在。如果取一个整指数值(一个完整的二进制文件)并称之为";"特殊";,你也许可以处理整个无穷大对NaN对正态对次正态格式显著提高效率--更少的时钟周期,更少的门--如果你试图让最高二进制数大部分正常,但只为无穷大和NaN雕刻了几个特殊的值。

需要记住的一件事是,当你设计硬件时(或微码、固件或软件)来实现这一点,您必须处理所有的情况,以及每个操作。无穷大和NaN既可以发生在输入上也可以发生在输出上,几乎任何操作。已经有很多特殊情况了,增加更多可能会导致事情失控。(问问英特尔,他曾经设法使浮点除法在输入的某个部分出现了相当大的错误。)

IEEE-754浮点的一个有用特性是潜在的位模式随着相应的值。零的位模式比最小子法线的位模式,以及位模式对于无穷大,比对于最大正规数多1。因此;改进的";该方案可能希望放置无穷大a在最后一个二进制值的顶部以下几步,使得NaN(或一些少量不同的NaN)可能在它之上(也就是说,没有像你建议的那样在0附近下跌)。

最后,可能值得指出的是,其他浮点格式通常也会浪费其价值的一小部分。例如,我相信DEC浮点格式(PDP-11和VAX)基本上只在零上消耗了整个二进制值

最新更新