C ++与Java原始浮点类型

时间:2014-10-07 08:32:15

标签: java c++ double rounding

这个问题适用于标准大师。

在解释浮点值时,典型的C ++编译器做了什么,Java没有,反之亦然。

现在我知道了如何存储浮点数的基础知识。我知道计算机不能完全代表那些不是2的幂的数字。

然而,我想到C ++以某种方式设法纠正了这个问题。例如,当用C ++(gcc)编译时,表达式0.15 + 0.15产生0.3,而在Java中则为0.30000000000000004 所以我的问题是双重的:

  1. 如果数字实际上在内部表示为0.30000000000000004,那么C ++编译器会做些什么来纠正它?它只是降低精度吗?仅在评估数字时才进行修正吗?有开销吗?或者它实际上以某种方式存储为0.3?

  2. 设计决策背后的原因是什么使Java不正确。这使得使用浮点基元成为Java的真正痛苦(是的,我知道BigDecimal等)?这种方式更快吗?它更正确吗?

  3. 如果Java方式背后有一个好处,我会很高兴听到它。

    我真的很想听听双方的意见。这是编程语言设计研究。

1 个答案:

答案 0 :(得分:4)

Java中浮点值的使用实际上存在一些差异。

但不是你观察到的:两种语言中0.15 + 0.15不是0.3(因为0.15也不是0.15)。

通常,差异不在编译器中,而在于运行时计算的完成方式。

在C ++中,它显然都依赖于平台。并且对于编译器选项,使用处理器的一些浮点单元等等......

在Java中,有两种模式可用于浮点计算。

第一种是默认模式,它允许JVM(自1.2起)在计算过程中使用更高的精度。因此,如果您添加两个浮点值(例如32位),则中间结果可以以60位精度存储 - 但这是高度平台依赖的!这可能会产生一些分歧。

为避免这种情况,您可以在类,接口和非抽象方法上使用strictfp关键字。然后将所有中间结果截断为您使用的类型的精度(浮点数为32位,双精度值为64位)。

  

如果Java方式背后有一个好处,我会很高兴听到它。

默认方式没有任何好处,经常受到批评。使用strictfp关键字可能会对可移植性产生一些好处。