当前位置: 首页 > 知识库问答 >
问题:

机器ε与浮点舍入误差有什么关系?

微生欣怡
2023-03-14

我已经读到,由于尾数中的位数有限,浮点可能会遇到舍入。另外,我读到机器ε表示一个浮点,使得1ε等于下一个最小可表示数。

a) 然而,我无法连接ε和舍入误差之间的关系。有人能用外行的语言解释一下它们之间的关系吗?

b)ε是否只依赖于用于尾数的位,甚至用于指数的位也在确定ε中起作用?

c) 1/3是如何用浮点表示的?我知道它是0.3(重复出现),但接下来呢?从这里开始,它将如何以二进制形式表示?

共有1个答案

咸承教
2023-03-14

我已经读到,由于尾数中的位数有限,浮点可能会遇到舍入。

每个固定大小的数字格式都可能会由于有限的位数而遇到错误,包括整数格式、浮点格式、定点格式和有理数格式。实数算术有无穷多的结果可以通过算术运算获得,因此任何具有有限位数的格式都不能代表所有可能的结果。

浮点数分数部分的首选术语是“有效位”“尾数”是一个古老的术语,表示对数的分数部分。尾数是对数的(在尾数上加上一些东西会乘以表示的数字)。有效位是对数的(向有效位中添加某些内容会增加所表示的数字,尽管按指数缩放,但不受原始有效位的影响)。

另外,我读到机器ε表示一个浮点,使得1ε等于下一个最小可表示数。

这是机器ε的一个常见但不正确的定义,或者至少表述得很糟糕。下面有更多信息。

浮点表示的一种形式是M•be,其中:

  • M是一个整数,限制在一定的范围内。对于IEEE-754"单"格式,也称为binary32,−16,777,216

另一种形式的浮点表示法±M•be,其中:

  • M是一个二进制数字,在小数点之前有一位(一般相当于小数点),在小数点之后有固定位数。对于binary32,这是点后23位,所以总共24位

这两种形式是等价的:任何一种格式中表示的每个数字都可以在另一种格式中表示。要在二进制32格式的形式之间进行更改,请将第一种格式的M除以223(这样就产生了一个二进制数字,其点前有一位数字,点后有23位数字),然后将23添加到e中(这样就补偿了除法,并在所需的间隔中产生了一个新的e),或者对相反的方向进行反向操作。

我们可以自由选择使用哪种形式,这两种形式对不同的目的有用。后者在规范中最常见,但前者对一些数值分析很有用,这就是我介绍它的原因。此外,有时符号被写成−1的幂:(−1)s•M•be,其中符号位,s,是0或1。

现在我们可以考虑算术中出现的舍入误差。

假设我们做了一些运算,无论是加法、减法、乘法、除法还是其他运算,它有一个实数算术结果x,我们想把它转换成浮点格式。让我们写x=M•be,其中M=x,e=0。然后我们可以通过将M乘以或除以b来调整它,直到它尽可能大,而不超过M的界限。我们还可以调整e来补偿我们乘以或除以b的次数。然后我们有一个新的M和一个新的e,仍然是x=M•be

如果这个新的M是一个整数,e是有界的,我们就完成了,我们有x在所需的形式。x可以用浮点格式表示,操作可以产生这个结果,没有舍入误差。

因为问题是关于舍入误差的,所以我假设e在范围内,并且保持不变。如果超出范围,则会导致溢出或下溢,但我不会讨论这些异常结果。

如果M不是整数,则x不能用浮点格式表示。由于M是通过调整e而不超出有效位界限所能达到的最大值,因此无法消除M的分数部分,并按照形式要求使M成为整数。我们能产生的最佳结果是将M四舍五入到最接近的整数。

有几种四舍五入规则,包括:

  • 在任意方向将M四舍五入到最接近的整数。如果有一个平局(分数正好是½),则圆可以使M相等。这通常是默认规则
  • 向上,向上∞. (这使得正M的大小变大,负M的大小变小。)
  • 向下转,朝−∞. (与上述相反。)
  • 接近零。(这会使所有非整数M的大小变小。)
  • 舍入使M为奇数,即使最近的偶数整数比最近的奇数整数更接近。(这是一种特殊的舍入模式,对于中间操作非常有用,因为它保留了非零分数部分的信息。)

现在我们准备回答这个问题:

a) 然而,我无法连接ε和舍入误差之间的关系。有人能用外行的语言解释一下它们之间的关系吗?

舍入误差有多大?根据第一个四舍五入规则,我们移动M使其成为整数的最远距离是½。这是因为,对于两个连续整数n和n1之间的每个数字,从数字到n的距离是½或更小,或者从数字到n1的距离是½或更小(或者两者都是)。(你只能走到森林的一半,因为在那之后,你就要出去了。)

因此,如果四舍五入到最近,最大四舍五入误差为M单位的½。回想一下,M由be缩放,因此绝对误差最多为½•be。be称为最小精度单位(ULP),因此最大绝对误差为½ULP。请注意,ULP的变化取决于所表示的数字,它由be缩放,因此1的ULP不同于128的ULP或1/256的ULP。

使用其他四舍五入规则,我们可以将M调整到1。例如,如果真实结果的分数部分为0.99,并且我们正四舍五入到零,我们可以将M调整到0.99,以获得零方向的下一个整数。

机器ε是1的ULP。

在二进制32的第一种浮点形式中,1表示为8388608•2−23。所以这个的ULP是1•2−23。在第二种形式中,1表示为1.000000000000000000000002•20。将其向上调整1 ULP会产生1.0000000000000000012•20,这是0.00000000000000000012•20,等于2−23

现在我们可以明白为什么问题中的定义是错误的或表述不当。它通常表示为ε是最小的e,因此1e!=1,这意味着它是第一个数字,因此将其与1相加会产生1之后的下一个数字。在那场演讲中,这是错误的。要知道为什么,考虑添加1(8388608·2)−23)和3•2−25。实数结果为8388608.75•2−23。为了得到一个有代表性的结果,我们必须将其四舍五入到8388609−23,从而得到下一个大于1的可表示值。但是1的ULP应该是2−23,也就是4•2−25,大于3•2−25。因此,根据该定义,ULP不是最小的数字,因此将其与1相加产生下一个可表示的数字。这不是我们想要的定义。

的确,机器ε是最小的数e,因此1e的实数算术结果是下一个可表示的数。但是,如果我们这样表述定义,由于上面的舍入,我们必须清楚我们想要的是1e的实数结果,而不是计算的浮点结果。我们可以说机器ε是1和下一个大于1的可表示值之间的差。

b)ε是否只依赖于用于尾数的位,甚至用于指数的位也在确定ε中起作用?

如上所述,当我们使用第一种形式时,其中M是一个整数,ULP只是缩放部分,be。但要知道指数是多少,我们必须根据可用的界限计算M。正如你在上面看到的,为了以这种形式表示1,我们必须对其进行缩放,得到8388608•2−23,我们从中看到ULP为2−23。在第二种形式中,我们可以直接使用1作为有效位,而无需调整它,将1表示为1.000000000000000000000002•20。但是,为了计算ULP,我们必须计算出M的低位的位置值。因此,无论哪种方式,有效位的宽度和指数的值都会在确定ULP时发挥作用。

c) 1/3是如何用浮点表示的?我知道它是0.3(重复出现),但接下来呢?从这里开始,它将如何以二进制形式表示?

⅓ 无法以二进制浮点格式表示。如果我们将其按两次幂中的最大幂进行缩放,将其保持在224以下,我们得到⅓ = 11,184,810⅔•2−25。在binary32格式中,最接近的是将其四舍五入到11184811•2−25,即0.3333333432674407958984375。

 类似资料:
  • 我不明白为什么这是1.0。它不应该是0.999999999999吗?因此,我提出了一种解决方案,python对其答案进行了自动舍入,但如果大于,则无法解释以下结果。。。 我以为四舍五入错误是因为尾数中使用的位数有限,指数(浮点数),但0.9999~~9也没有超出位数的限制...有人能解释一下为什么这些结果会这样吗?

  • 问题内容: 我不知道这是否是一个明显的错误,但是在运行Python脚本以更改模拟参数时,我意识到缺少和的结果。在调查中,我注意到以下Python代码: 生成的相同文件的增量= 0.28和0.29,与.57和.58相同,原因是python返回float(29)/ 100为。但这不是系统错误,从某种意义上说,它并不是每个整数都发生的。因此,我创建了以下Python脚本: 而且我看不到发生这种舍入错误的

  • 我有一个关于PostgreSQL 9.2中浮点数的新手问题。 有没有直接舍入浮点数的函数,即不需要先将数字转换为数字类型? 另外,我想知道是否有一个函数可以用任意的度量单位进行取整,例如精确到0.05? 首先将数字转换为十进制形式时,以下查询工作正常: 然而,我真正想要实现的是以下几点: 这当前给了我以下错误: 谢啦

  • 我正在用Java开发一个时间关键型算法,因此没有使用。为了处理舍入误差,我设置了一个误差上限,在这个上限之下,不同的浮点数被认为是完全相同的。现在的问题是,这个界限应该是什么?或者换句话说,当对浮点数(浮点数加、减、乘、除)执行计算操作时,可能出现的最大舍入误差是什么? 通过我做的一个实验,似乎的范围就足够了。 PS:这个问题与语言无关。 编辑:我使用的是数据类型。这些数字是通过的方法生成的。 编

  • 问题内容: 我期望的是0.313而不是0.312,为什么会这样呢?还有其他方法可以用来获得0.313吗? 谢谢 问题答案: Python 3使用舍入到偶数方法根据IEEE 754标准进行舍入。 如果您想采用另一种方式取整,则只需手动实施即可: 用法示例: 注意: 在python2中,舍入总是远离零,而在python3中,它舍入为偶数。(例如,请参见功能文档中的2.7和3.3之间的区别)。

  • 我正在努力更好地理解浮点运算。我知道机器ε(e)的定义是1和下一个最大数之间的差(即1之后的下一个最大数可以用浮点精确表示为1E)。 然而,当我乘以(1e)*(1e)时,浮点值会得到什么?理论上它应该是12*e^2,但是(假设e