两个 IEEE754 数字的舍入说明

问题描述 投票:0回答:1

最近我一直在为我的自定义语言创建一个标准库。该库包含一些软浮点功能,因为我的目标处理器没有 FPU。我不支持双精度浮点数,我只支持单精度,因为我的目标架构是 32 位。

目前我已经定义了所有浮点函数,但是我还没有实现任何类型的舍入。

我的编译器是用 Java 编写的,我目前有一些测试用例,它们在源程序上运行解释器并在虚拟机中运行我的自定义 IR,然后比较结果以确保其匹配。

Ir 虚拟机利用我的软浮点功能,而解释器则通过 Java 操作完成所有操作。原因是解释源未链接,但 Ir 模块静态链接到标准库并包含软浮点运算。解释器支持标准库调用,但该功能实际上内置于解释器中,而不是从我的源语言的库文件中提取。

由于上述原因,解释器给我的结果与我链接的红外模块不同。

我的口译员输出如下

H is 1
I is 3.141593
H is 1
I is 3.141593
6

我的红外模块输出如下

H is 1
I is 3.1415925
H is 1
I is 3.1415925
H is 1
I is 3.1415925
H is 1
I is 3.1415925
3.8146973E-6

现在您可以忽略底部数字的不同。 IR 模块中还有更多线路。我想知道的是为什么在解释器中除以 355 / 113 并得到 3.141593 而不是 3.1415925 。

更具体地说,我知道为什么会这样,因为我还没有实现舍入功能。

ICode Vm result    | 3.1415925 | 01000000010010010000111111011010
Interpreter result | 3.141593  | 01000000010010010000111111011100

所以我的问题是为什么它以这种方式四舍五入。就像为什么是第二位而不是第一位被四舍五入,或者在这种情况下会保持不变,因为它们都是零。

我在网上寻找了几种解决方案,然后我想出了一些关于粘性位和一堆我不太理解的其他奇怪的东西。只是想有人可能比我更了解这里的 ieee754 标准。

floating-point rounding ieee-754 ieee
1个回答
0
投票

355除以113,商为+21•1.1001 0010 0001 1111 1011 0111 1000 0001 0010 0001 1111…2.

IEEE-754 二进制 32 格式的有效数有 24 位,因此我们需要在标有“^”的点对该有效数进行舍入: 1.1001 0010 0001 1111 1011 011^1 1000 0001 0010 0001 1111…2.

IEEE-754 没有规定必须使用哪种舍入方法。它提供了一个选择。您可以向下舍入,向 −∞ 方向舍入,这将产生 1.1001 0010 0001 1111 1011 0112

您可以向上舍入,向 +∞ 方向舍入,这将产生 1.1001 0010 0001 1111 1011 1002。请注意,这是上述值之后的下一个可表示值。我们只是将有效数增加到下一步。

您可以向零舍入,对于正数,这会产生与向 −∞ 舍入相同的结果。

最常见的方法(也是默认方法)是四舍五入到最接近的可表示值,如果存在平局,则四舍五入到偶数低位的选择。 (十进制格式还有一种特殊情况,此处不相关。)

在 1.1001 0010 0001 1111 1011 011^1 1000 0001 0010 0001 1111…2 中,向下舍入会在标有“^”的舍入点处产生 1 1000…2 的差异。舍入导致舍入点处的差异为 0 0111...。数字越大,结果越接近准确。因此,四舍五入到最接近的值会产生更大的数字,+21•1.1001 0010 0001 1111 1011 1002。即 3.14159297943115234375。

© www.soinside.com 2019 - 2024. All rights reserved.